Если вы хотите запросить базу данных, вы должны использовать что-то вроде slick , которая является современной библиотекой запросов и доступа к базе данных для Scala.
быстрый пример slick:
case class User(id: Option[Int], first: String, last: String)
class Users(tag: Tag) extends Table[User](tag, "users") {
def id = column[Int]("id", O.PrimaryKey, O.AutoInc)
def first = column[String]("first")
def last = column[String]("last")
def * = (id.?, first, last) <> (User.tupled, User.unapply)
}
val users = TableQuery[Users]
тогда вам нужно создать конфигурацию для вашей базы данных:
mydb = {
dataSourceClass = "org.postgresql.ds.PGSimpleDataSource"
properties = {
databaseName = "mydb"
user = "myuser"
password = "secret"
}
numThreads = 10
}
, и в вашем коде вы загружаете конфигурацию:
val db = Database.forConfig("mydb")
, затем выполните свой запрос с помощью метода db.run, которыйдает вам будущее как результат, например, вы можете получить все строки, вызвав метод result
val allRows: Future[Seq[User]] = db.run(users.result)
этот запрос выполняется без блокировки текущего потока.
Если у вас есть задача, выполнение которой занимает много времениили для вызова другой службы вы должны использовать фьючерсы.
Примером этого является простой HTTP-вызов внешней службы.Вы можете найти пример в здесь
Если у вас есть задача, выполнение которой занимает много времени и для этого, вы должны сохранять изменяемые состояния, в этом случае лучшим вариантом будет использование Akka Actorsкоторые инкапсулируют ваше состояние внутри субъекта, который решает проблему параллелизма и безопасности потоков настолько просто, насколько это возможно. Примеры задач suck:
import akka.actor.Actor
import scala.concurrent.Future
case class RegisterEndpoint(endpoint: String)
case class NewUpdate(update: String)
class UpdateConsumer extends Actor {
val endpoints = scala.collection.mutable.Set.empty[String]
override def receive: Receive = {
case RegisterEndpoint(endpoint) =>
endpoints += endpoint
case NewUpdate(update) =>
endpoints.foreach { endpoint =>
deliverUpdate(endpoint, update)
}
}
def deliverUpdate(endpoint: String, update: String): Future[Unit] = {
Future.successful(Unit)
}
}
Если вы хотите обрабатывать огромное количество живых данных или соединение через веб-сокет,обработка файла CSV, который растет со временем, ... или т. д., лучший вариант - поток Akka.Например, чтение данных из темы кафки с помощью Alpakka: Alpakka kafka разъем