132 lines
5.3 KiB
Kotlin
132 lines
5.3 KiB
Kotlin
package codes.kalar.service
|
|
|
|
import codes.kalar.exception.DbElementNotFoundException
|
|
import codes.kalar.model.NewPatron
|
|
import codes.kalar.model.Patron
|
|
import java.sql.*
|
|
|
|
class PatronService(private val connection: Connection) {
|
|
|
|
companion object {
|
|
private const val SELECT_PATRON_BY_ID = "SELECT * FROM patron WHERE id = ?"
|
|
private const val SELECT_PATRON_BY_LOGIN_USERNAME = "SELECT * From patron where login_username = ?"
|
|
private const val INSERT_PATRON =
|
|
"INSERT INTO patron (name, has_good_standing, fee_total, is_archived, login_username, last_login, password) VALUES (?, ?, ?, ?, ?, ?, ?)"
|
|
private const val UPDATE_PATRON_BY_ID =
|
|
"UPDATE patron SET name = ?, has_good_standing = ?, fee_total = ?, is_archived = ?, login_username = ?, " +
|
|
"last_login = ?, password = ? WHERE id = ?"
|
|
|
|
// In the event are "deleted" erroneously, having a flag set instead of actually removing the entry allows
|
|
// for quick reversal.
|
|
private const val ARCHIVE_PATRON_BY_ID = "UPDATE patron set is_archived = true WHERE id = ?"
|
|
}
|
|
|
|
fun create(newPatron: NewPatron): Long {
|
|
val statement = connection.prepareStatement(INSERT_PATRON, Statement.RETURN_GENERATED_KEYS)
|
|
statement.setString(1, newPatron.name)
|
|
statement.setBoolean(2, true)
|
|
statement.setLong(3, 0)
|
|
statement.setBoolean(4, false)
|
|
statement.setString(5, newPatron.loginUsername)
|
|
statement.setDate(6, Date(System.currentTimeMillis()))
|
|
statement.setString(7, newPatron.password)
|
|
statement.execute()
|
|
try {
|
|
val key = statement.generatedKeys
|
|
if (key.next()) {
|
|
return key.getLong(1)
|
|
}
|
|
return -1
|
|
} catch (cause: SQLException) {
|
|
throw DbElementNotFoundException("Couldn't insert patron ${newPatron.name} into database. ${cause.message}")
|
|
}
|
|
}
|
|
|
|
fun readPatronById(id: Long): Patron {
|
|
try {
|
|
val statement = connection.prepareStatement(SELECT_PATRON_BY_ID, Statement.RETURN_GENERATED_KEYS)
|
|
statement.setLong(1, id)
|
|
val resultSet = statement.executeQuery()
|
|
if (resultSet.next()) {
|
|
val patron = createPatronFromResults(resultSet)
|
|
return patron
|
|
} else {
|
|
throw DbElementNotFoundException("Patron with ID $id not found")
|
|
}
|
|
} catch (cause: SQLException) {
|
|
throw DbElementNotFoundException("Patron with ID $id is not found")
|
|
}
|
|
}
|
|
|
|
fun readPatronByLoginUsername(username: String): Patron {
|
|
try {
|
|
val statement = connection.prepareStatement(SELECT_PATRON_BY_LOGIN_USERNAME)
|
|
statement.setString(1, username)
|
|
val resultSet = statement.executeQuery()
|
|
if (resultSet.next()) {
|
|
val patron = createPatronFromResults(resultSet)
|
|
return patron
|
|
} else {
|
|
throw SQLException()
|
|
}
|
|
} catch (cause: SQLException) {
|
|
throw DbElementNotFoundException("Could not find username or password")
|
|
}
|
|
}
|
|
|
|
fun loginPatronByLoginUsername(username: String, password: String): Boolean {
|
|
try {
|
|
val statement = connection.prepareStatement(SELECT_PATRON_BY_LOGIN_USERNAME)
|
|
statement.setString(1, username)
|
|
val resultSet = statement.executeQuery()
|
|
return if (resultSet.next()) {
|
|
resultSet.getString("password") == password && !resultSet.getBoolean("is_archived")
|
|
} else {
|
|
throw SQLException()
|
|
}
|
|
} catch (cause: SQLException) {
|
|
throw DbElementNotFoundException("Could not find username or password")
|
|
}
|
|
}
|
|
|
|
fun update(patron: Patron): Boolean {
|
|
val statement = connection.prepareStatement(UPDATE_PATRON_BY_ID)
|
|
statement.setString(1, patron.name)
|
|
statement.setBoolean(2, patron.hasGoodStanding)
|
|
statement.setLong(3, patron.feeTotal)
|
|
statement.setBoolean(4, patron.isArchived)
|
|
statement.setString(5, patron.loginUsername)
|
|
statement.setString(6, patron.lastLogin)
|
|
statement.setString(7, patron.password)
|
|
statement.setLong(8, patron.id)
|
|
try {
|
|
return !statement.execute()
|
|
} catch (cause: SQLException) {
|
|
throw DbElementNotFoundException("Patron with ID ${patron.id} not found.")
|
|
}
|
|
}
|
|
|
|
fun delete(id: Long) {
|
|
val statement = connection.prepareStatement(ARCHIVE_PATRON_BY_ID)
|
|
statement.setLong(1, id)
|
|
try {
|
|
statement.execute()
|
|
} catch (cause: SQLException) {
|
|
throw DbElementNotFoundException("Patron with ID $id not found.")
|
|
}
|
|
}
|
|
|
|
fun createPatronFromResults(resultSet: ResultSet): Patron {
|
|
return Patron(
|
|
id = resultSet.getLong("id"),
|
|
name = resultSet.getString("name"),
|
|
hasGoodStanding = resultSet.getBoolean("has_good_standing"),
|
|
feeTotal = resultSet.getLong("fee_total"),
|
|
isArchived = resultSet.getBoolean("is_archived"),
|
|
lastLogin = resultSet.getString("last_login"),
|
|
password = "", // For security reasons...
|
|
loginUsername = resultSet.getString("login_username")
|
|
)
|
|
}
|
|
}
|