Sto lavorando su un progetto Scala e Wartremover mostra un errore sull'utilizzo di Option#get
nel mio codice:
Option#get is disabled - use Option#fold instead
Mentre capisco come spesso si dovrebbe evitare get
, penso che ci siano casi in cui è ragionevole usarlo, come il mio attuale: in primo luogo, creo un elemento di risposta (nel database), quindi voglio restituisci la risposta appena creata leggendola da lì.
def create(answer: Answer): Future[Answer] = {
writeToDb(answer) // returns Future[Long]
.flatMap(
readFromDb(_) // returns Future[Option[Answer]]
.map(_.get) // Wartremover complains here
)
}
La mia comprensione è che get
dovrebbe generalmente essere evitato perché interrompe il flusso di controllo in caso di None
, come viene generata un'eccezione.
Tuttavia, mi aspetto che il mio Option
qui contenga sempre una risposta, poiché l'ho appena creato.
Se non c'è, c'è probabilmente un bug nel mio codice o un problema con il database.
In tal caso sarebbe irragionevole ricorrere a un valore predefinito o null
. Preferirei lanciare un'eccezione o mappare direttamente a un futuro in errore.
Un'alternativa a get
corrisponde in modo esplicito all'opzione:
def create(answer: Answer): Future[Answer] = {
writeToDb(answer) // returns Future[Long]
.flatMap(
readFromDb(_) // returns Future[Option[Answer]]
.flatMap {
case Some(answer) => Future.successful(answer)
case None => Future.failed(
new IllegalStateException("Failed to load answer after creation"))
}
)
}
Tuttavia, questo è molto più verboso pur ottenendo quasi lo stesso risultato di un semplice _.get
.
Mi sto perdendo qualcosa qui? O è solo un falso positivo di Wartremover?