auth;admin;password interfaces

This commit is contained in:
Your Name 2025-01-21 12:25:49 +03:00
parent 92c45f1165
commit a9a24b78e2
17 changed files with 442 additions and 194 deletions

View File

@ -10,6 +10,7 @@ repositories {
} }
dependencies { dependencies {
implementation("io.github.serpro69:kotlin-faker:2.0.0-rc.7")
testImplementation(kotlin("test")) testImplementation(kotlin("test"))
} }

View File

@ -1,152 +1,162 @@
import model.AdminUser import data.features.authorize.AuthorizeRepositoryImpl
import model.DefaultUser import domain.Service.authorize.AuthorizeServiceImpl
import model.ManagerUser
import model.User import model.User
import java.security.SecureRandom import ui.model.AuthorizeUI
import java.security.spec.KeySpec
import java.time.LocalDate
import javax.crypto.SecretKey
import javax.crypto.SecretKeyFactory
import javax.crypto.spec.PBEKeySpec
import java.util.Base64
val authorizeList = mutableListOf<User>() //val authorizeList = mutableListOf<User>()
val salt = "sallllt" //val salt = "sallllt"
private const val HASH_LENGTH = 256 //private const val HASH_LENGTH = 256
private const val ITERATIONS = 65536 //private const val ITERATIONS = 65536
//fun main(){
// authorizeList.add(AdminUser(email = "@1", password = hashPassword("qwerty123", salt), login = "aboba", lastAuthorizeDate = LocalDate.of(2022, 11, 25), userId = 1))
// authorizeList.add(ManagerUser(email = "@2", password = hashPassword("qwerty123", salt), login = "abiba", lastAuthorizeDate = LocalDate.of(2023, 3, 10), userId = 2))
// authorizeList.add(DefaultUser(email = "@3", password = hashPassword("qwerty123", salt), login = "abobus", lastAuthorizeDate = LocalDate.of(2023, 5, 15), userId = 3))
//
// while (true){
// println("1) registration")
// println("2) authorization")
// var choosen = readln()
// if (choosen == "1"){
// authorizeList.add(registration())
// authorizeList.forEach{
// println(it.userId)
// println(it.email)
// println(it.password)
// println(it.login)
// }
// }
// else{
// println(authorization())
// }
// }
//}
//
//fun registration(): User{
// println("email")
// val userEmail = readlnOrNull()
// checkNotNull(userEmail)
// require(userEmail.contains("@")){
// "add @ to email"
// }
//
// println("password")
// val userPassword = readlnOrNull()
// checkNotNull(userPassword)
// require(userPassword.length >= 8){
// "more longer password"
// }
//
// println("password again")
// val userPasswordTwo = readlnOrNull()
// checkNotNull(userPasswordTwo)
// require(userPassword == userPasswordTwo){
// "nea"
// }
//
// println("login")
// val userLogin = readlnOrNull()
// checkNotNull(userLogin)
// require(userLogin.length >= 4){
// "more longer login"
// }
//
// println("1)admin, 2)manager, 3)defaultUser")
// val role = readlnOrNull()
// checkNotNull(role)
//
// return when(role){
// "1" -> return AdminUser(
// authorizeList.size + 1,
// login = userLogin,
// password = hashPassword(userPassword, salt),
// lastAuthorizeDate = LocalDate.now(),
// email = userEmail,
// )
// "2" -> return ManagerUser(
// authorizeList.size + 1,
// login = userLogin,
// password = hashPassword(userPassword, salt),
// lastAuthorizeDate = LocalDate.now(),
// email = userEmail,
// )
// "3" -> return DefaultUser(
// authorizeList.size + 1,
// login = userLogin,
// password = hashPassword(userPassword, salt),
// lastAuthorizeDate = LocalDate.now(),
// email = userEmail,
// )
//
// else -> {throw IllegalArgumentException("error")}
// }
//}
//
//fun authorization(): String{
// var adminChoose = true
// println("email")
// val userEmail = readlnOrNull()
// checkNotNull(userEmail)
// val user = authorizeList.find { it.email == userEmail }
// require(user != null){
// "no user with that email"
// }
//
// println("password")
// val userPassword = readlnOrNull()
// checkNotNull(userPassword)
// require(user.password == hashPassword(userPassword, salt)){
// "incorrect password"
// }
//
// if (user is AdminUser){
// while (adminChoose == true){
// adminChoose = adminFunc(user)
// }
// }
//
// return "agada"
//}
//
//fun adminFunc(user: AdminUser): Boolean{
// println("1) вывести всех пользователей")
// println("2) поменять пароль пользователя")
// println("3) удалить пользователя")
// println("4) вывести с сортировкой по убыванию")
// println("5) назад")
//
// var choosen = readln()
// when(choosen){
// "1" -> user.allUsers(authorizeList)
// "2" -> user.changeUserPassword(authorizeList)
// "3" -> user.removeUser(authorizeList)
// "4" -> user.allUsersSorted(authorizeList)
// "5" -> return false
// }
// return true
//}
//
//fun hashPassword(password: String, salt: String): String {
// val saltBytes = Base64.getDecoder().decode(salt)
// val spec = PBEKeySpec(password.toCharArray(), saltBytes, ITERATIONS, HASH_LENGTH)
// val factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA256")
// val hash = factory.generateSecret(spec).encoded
// return Base64.getEncoder().encodeToString(hash)
//}
fun main(){ fun main(){
authorizeList.add(AdminUser(email = "@1", password = hashPassword("qwerty123", salt), login = "aboba", lastAuthorizeDate = LocalDate.of(2022, 11, 25), userId = 1)) val authorizeRepositoryImpl = AuthorizeRepositoryImpl()
authorizeList.add(ManagerUser(email = "@2", password = hashPassword("qwerty123", salt), login = "abiba", lastAuthorizeDate = LocalDate.of(2023, 3, 10), userId = 2)) val authorizeServiceImpl = AuthorizeServiceImpl(authorizeRepositoryImpl)
authorizeList.add(DefaultUser(email = "@3", password = hashPassword("qwerty123", salt), login = "abobus", lastAuthorizeDate = LocalDate.of(2023, 5, 15), userId = 3)) val authorizeUI = AuthorizeUI(authorizeServiceImpl)
while (true){ while(true){
println("1) registration") println("1)registration")
println("2) authorization") println("2)authorization")
var choosen = readln() val choosen = readlnOrNull()
if (choosen == "1"){ if (choosen == "1"){
authorizeList.add(registration()) authorizeUI.registration()
authorizeList.forEach{ }else{
println(it.userId) authorizeUI.authorize()
println(it.email)
println(it.password)
println(it.login)
}
}
else{
println(authorization())
} }
} }
} }
fun registration(): User{
println("email")
val userEmail = readlnOrNull()
checkNotNull(userEmail)
require(userEmail.contains("@")){
"add @ to email"
}
println("password")
val userPassword = readlnOrNull()
checkNotNull(userPassword)
require(userPassword.length >= 8){
"more longer password"
}
println("password again")
val userPasswordTwo = readlnOrNull()
checkNotNull(userPasswordTwo)
require(userPassword == userPasswordTwo){
"nea"
}
println("login")
val userLogin = readlnOrNull()
checkNotNull(userLogin)
require(userLogin.length >= 4){
"more longer login"
}
println("1)admin, 2)manager, 3)defaultUser")
val role = readlnOrNull()
checkNotNull(role)
return when(role){
"1" -> return AdminUser(
authorizeList.size + 1,
login = userLogin,
password = hashPassword(userPassword, salt),
lastAuthorizeDate = LocalDate.now(),
email = userEmail,
)
"2" -> return ManagerUser(
authorizeList.size + 1,
login = userLogin,
password = hashPassword(userPassword, salt),
lastAuthorizeDate = LocalDate.now(),
email = userEmail,
)
"3" -> return DefaultUser(
authorizeList.size + 1,
login = userLogin,
password = hashPassword(userPassword, salt),
lastAuthorizeDate = LocalDate.now(),
email = userEmail,
)
else -> {throw IllegalArgumentException("error")}
}
}
fun authorization(): String{
var adminChoose = true
println("email")
val userEmail = readlnOrNull()
checkNotNull(userEmail)
val user = authorizeList.find { it.email == userEmail }
require(user != null){
"no user with that email"
}
println("password")
val userPassword = readlnOrNull()
checkNotNull(userPassword)
require(user.password == hashPassword(userPassword, salt)){
"incorrect password"
}
if (user is AdminUser){
while (adminChoose == true){
adminChoose = adminFunc(user)
}
}
return "agada"
}
fun adminFunc(user: AdminUser): Boolean{
println("1) вывести всех пользователей")
println("2) поменять пароль пользователя")
println("3) удалить пользователя")
println("4) вывести с сортировкой по убыванию")
println("5) назад")
var choosen = readln()
when(choosen){
"1" -> user.allUsers(authorizeList)
"2" -> user.changeUserPassword(authorizeList)
"3" -> user.removeUser(authorizeList)
"4" -> user.allUsersSorted(authorizeList)
"5" -> return false
}
return true
}
fun hashPassword(password: String, salt: String): String {
val saltBytes = Base64.getDecoder().decode(salt)
val spec = PBEKeySpec(password.toCharArray(), saltBytes, ITERATIONS, HASH_LENGTH)
val factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA256")
val hash = factory.generateSecret(spec).encoded
return Base64.getEncoder().encodeToString(hash)
}

View File

@ -0,0 +1,9 @@
package data.features.admin
import domain.Response.UserResponse
import java.util.*
interface AdminRepository {
fun removeUserById(userId: UUID): Boolean
fun getAllUsers(): List<UserResponse>
}

View File

@ -0,0 +1,28 @@
package data.features.admin
import data.features.authorize.users
import domain.Response.UserResponse
import java.util.UUID
class AdminRepositoryImpl: AdminRepository{
override fun removeUserById(userId: UUID): Boolean {
return users.removeIf{it.uuid == userId}
}
override fun getAllUsers(): List<UserResponse> {
var usersResponse = mutableListOf<UserResponse>()
for (user in users){
usersResponse.add(
UserResponse(
firstName = user.firstName,
lastName = user.lastName,
email = user.email,
number = user.number,
address = user.address,
photo = user.photo
)
)
}
return usersResponse
}
}

View File

@ -0,0 +1,10 @@
package data.features.authorize
import domain.Request.AuthorizeRequest
import domain.Request.RegistrationRequest
import domain.Response.UserResponse
interface AuthorizeRepository {
fun auth(authorizeRequest: AuthorizeRequest): UserResponse
fun registration(request: RegistrationRequest): UserResponse
}

View File

@ -0,0 +1,62 @@
package data.features.authorize
import data.features.model.UserDTO
import data.features.password.PasswordRepository
import data.features.password.PasswordRepositoryImpl
import domain.Request.AuthorizeRequest
import domain.Request.RegistrationRequest
import domain.Response.UserResponse
import io.github.serpro69.kfaker.Faker
import model.User
import java.util.*
import javax.crypto.SecretKeyFactory
import javax.crypto.spec.PBEKeySpec
private val passwordRepository = PasswordRepositoryImpl()
val users = generateUsers(100).toMutableList()
class AuthorizeRepositoryImpl: AuthorizeRepository {
override fun auth(authorizeRequest: AuthorizeRequest): UserResponse {
val userEmail = authorizeRequest.email
val user = users.find { it.email == userEmail }
require(user != null){
"no user with that email"
}
val password = passwordRepository.hashedPassword(authorizeRequest.password, "salt".toByteArray())
val authed = passwordRepository.matches(authorizeRequest.password, "salt".toByteArray(), user.password)
if (authed){
println("dodo")
}else{
println("nono")
}
return UserResponse(user.firstName, user.lastName, user.email, user.number, user.address, user.photo)
}
override fun registration(request: RegistrationRequest): UserResponse {
val newUser = UserDTO(uuid = UUID.randomUUID(), email = request.email, password = passwordRepository.hashedPassword(request.password, "salt".toByteArray()), firstName = request.firstName)
users.add(newUser)
return UserResponse(newUser.firstName, newUser.lastName, newUser.email, newUser.number, newUser.address, newUser.photo)
}
}
fun generateUsers(userCount: Int): List<UserDTO>{
val localUserList = mutableListOf<UserDTO>()
val faker = Faker()
repeat(userCount){
localUserList.add(
UserDTO(
uuid = UUID.randomUUID(),
firstName = faker.name.firstName(),
lastName = faker.name.lastName(),
email = faker.random.randomString(3)+"@mail.ru",
password = passwordRepository.hashedPassword(faker.random.randomString(12), "salt".toByteArray()),
number = faker.phoneNumber.phoneNumber(),
address = faker.address.fullAddress(),
photo = faker.file.toString()
)
)
}
return localUserList
}

View File

@ -0,0 +1,15 @@
package data.features.model
import java.util.*
import kotlin.uuid.Uuid
data class UserDTO(
val uuid: UUID,
var firstName: String,
var lastName: String? = null,
var email: String,
var password: String,
var number: String? = null,
var address: String? = null,
var photo: String? = null
)

View File

@ -0,0 +1,6 @@
package data.features.password
interface PasswordRepository {
fun hashedPassword(password: String, salt:ByteArray): String
fun matches(password: String, salt:ByteArray, hashedPassword: String): Boolean
}

View File

@ -0,0 +1,20 @@
package data.features.password
import javax.crypto.SecretKeyFactory
import javax.crypto.spec.PBEKeySpec
import java.util.Base64
private const val HASH_LENGTH = 256
private const val ITERATIONS = 65536
class PasswordRepositoryImpl: PasswordRepository{
override fun hashedPassword(password: String, salt: ByteArray): String {
val spec = PBEKeySpec(password.toCharArray(), salt, ITERATIONS, HASH_LENGTH)
val factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA256")
val hash = factory.generateSecret(spec).encoded
return Base64.getEncoder().encodeToString(hash)
}
override fun matches(password: String, salt: ByteArray, hashedPassword: String): Boolean {
return hashedPassword == hashedPassword(password, salt)
}
}

View File

@ -0,0 +1,3 @@
package domain.Request
data class AuthorizeRequest(val email: String, val password: String)

View File

@ -0,0 +1,3 @@
package domain.Request
data class RegistrationRequest(val firstName: String, val email: String, val password: String)

View File

@ -0,0 +1,10 @@
package domain.Response
data class UserResponse(
val firstName: String,
val lastName: String? = null,
val email: String,
val number: String? = null,
val address: String? = null,
val photo: String? = null
)

View File

@ -0,0 +1,10 @@
package domain.Service.authorize
import domain.Request.AuthorizeRequest
import domain.Request.RegistrationRequest
import ui.model.UserPresenter
interface AuthorizeService {
fun auth(authorizeRequest: AuthorizeRequest): UserPresenter
fun registration(registrationRequest: RegistrationRequest): UserPresenter
}

View File

@ -0,0 +1,18 @@
package domain.Service.authorize
import data.features.authorize.AuthorizeRepository
import domain.Request.AuthorizeRequest
import domain.Request.RegistrationRequest
import ui.model.UserPresenter
class AuthorizeServiceImpl(private val authorizeRepository: AuthorizeRepository): AuthorizeService {
override fun auth(authorizeRequest: AuthorizeRequest): UserPresenter {
val user = authorizeRepository.auth(authorizeRequest)
return UserPresenter(firstName = user.firstName, lastName = user.lastName, email = user.email, photo = user.photo, number = user.number, address = user.address)
}
override fun registration(registrationRequest: RegistrationRequest): UserPresenter {
val user = authorizeRepository.registration(registrationRequest)
return UserPresenter(firstName = user.firstName, lastName = user.lastName, email = user.email, photo = user.photo, number = user.number, address = user.address)
}
}

View File

@ -1,50 +1,50 @@
package model //package model
//
import AdminInterface //import AdminInterface
import hashPassword //import hashPassword
import salt //import salt
import java.time.LocalDate //import java.time.LocalDate
//
class AdminUser( //class AdminUser(
userId: Int, // userId: Int,
email: String, // email: String,
login: String, // login: String,
password: String, // password: String,
lastAuthorizeDate: LocalDate, // lastAuthorizeDate: LocalDate,
) : User(userId, email, login, password, lastAuthorizeDate), AdminInterface{ //) : User(userId, email, login, password, lastAuthorizeDate), AdminInterface{
override fun allUsers(authorizeList: MutableList<User>){ // override fun allUsers(authorizeList: MutableList<User>){
for (user in authorizeList){ // for (user in authorizeList){
println(user.login) // println(user.login)
} // }
} // }
override fun changeUserPassword(authorizeList: MutableList<User>){ // override fun changeUserPassword(authorizeList: MutableList<User>){
println("email for update") // println("email for update")
val email = readln() // val email = readln()
println("new password") // println("new password")
val password = readln() // val password = readln()
//
val user = authorizeList.find { it.email == email } // val user = authorizeList.find { it.email == email }
require(user != null){ // require(user != null){
"no user with that email" // "no user with that email"
} // }
//
user.password = hashPassword(password, salt) // user.password = hashPassword(password, salt)
} // }
override fun removeUser(authorizeList: MutableList<User>){ // override fun removeUser(authorizeList: MutableList<User>){
println("email for removing") // println("email for removing")
val email = readln() // val email = readln()
//
val removed = authorizeList.removeIf{it.email == email} // val removed = authorizeList.removeIf{it.email == email}
if (removed){ // if (removed){
println("removed") // println("removed")
} else{ // } else{
println("didn't") // println("didn't")
} // }
} // }
override fun allUsersSorted(authorizeList: MutableList<User>){ // override fun allUsersSorted(authorizeList: MutableList<User>){
authorizeList.sortByDescending { it.lastAuthorizeDate } // authorizeList.sortByDescending { it.lastAuthorizeDate }
for(user in authorizeList){ // for(user in authorizeList){
println(user.login + " auth at " + user.lastAuthorizeDate) // println(user.login + " auth at " + user.lastAuthorizeDate)
} // }
} // }
} //}

View File

@ -0,0 +1,33 @@
package ui.model
import domain.Request.AuthorizeRequest
import domain.Request.RegistrationRequest
import domain.Service.authorize.AuthorizeService
class AuthorizeUI(val authorizeService: AuthorizeService) {
fun authorize(){
println("email")
val email = readlnOrNull()
println("password")
val password = readlnOrNull()
checkNotNull(email)
checkNotNull(password)
val user = authorizeService.auth(AuthorizeRequest(email = email, password = password))
println(user.firstName)
}
fun registration(){
println("firstName")
val firstName = readlnOrNull()
println("email")
val email = readlnOrNull()
println("password")
val password = readlnOrNull()
println()
checkNotNull(email)
checkNotNull(password)
checkNotNull(firstName)
val user = authorizeService.registration(RegistrationRequest(firstName, email, password))
println(user.firstName)
}
}

View File

@ -0,0 +1,10 @@
package ui.model
data class UserPresenter(
val firstName: String,
val lastName: String? = null,
val email: String,
val number: String? = null,
val address: String? = null,
val photo: String? = null
)