2017-08-06 152 views
0

我在写一个简单的基于scala的脚本,它应该将一些数据插入到Mongo集合中。问题是,该脚本在mongo完成任务之前退出。什么是解决这个问题,考虑下面的脚本惯用/最好的方法:Scala脚本等待mongo完成任务

#!/usr/bin/env scalas 
/*** 
scalaVersion := "2.12.2" 

libraryDependencies ++= { 
    Seq(
    "org.mongodb.scala" %% "mongo-scala-driver" % "2.1.0" 
) 
} 
*/ 
import org.mongodb.scala._ 

val mongoClient: MongoClient = MongoClient("mongodb://localhost") 
val database: MongoDatabase = mongoClient.getDatabase("dev") 

val doc: Document = Document("name" -> "MongoDB", "type" -> "database", 
    "count" -> 1, "info" -> Document("x" -> 203, "y" -> 102)) 

val collection: MongoCollection[Document] = database.getCollection("test") 

val subscription = new Observer[Completed] { 
    override def onNext(result: Completed): Unit = println("Inserted") 

    override def onError(e: Throwable): Unit = println("Failed"+e.toString) 

    override def onComplete(): Unit = println("Completed") 
} 

collection.insertOne(doc).subscribe(subscription) 

上面的脚本会产生执行时follwoing错误:

com.mongodb.MongoInterruptedException: Interrupted acquiring a permit to retrieve an item from the pool 

但是,如果我在结尾处添加Thread.sleep(3000)它完成得很好。

回答

0

我推荐使用Promise对象来通知完成异步作业。

http://www.scala-lang.org/api/2.12.1/scala/concurrent/Promise.html

异步作业完成或超时后,该程序将退出之后。

val promise = Promise[Boolean] 

... 

override def onError(e: Throwable): Unit = { 
    println("Failed"+e.toString) 
    promise.success(false) 
} 
override def onComplete(): Unit = { 
    println("Completed") 
    promise.success(true) 
} 

val future = promise.future 
Await.result(future, Duration(10, java.util.concurrent.TimeUnit.SECONDS)) 
//after completion, the program would exit.