2014-06-21 4 views
0

Rinofly의 play-s3 추상화를 사용하는 Amazon S3에서 zip 파일을 만드는 방법이 있습니다 (실제로 중요하지는 않습니다 - 중요한 것은 Future을 사용하는 것입니다). 메서드는 다음과 같이 보입니다.스칼라 내에서 예외 삼키는 방법 미래 메서드 체인

def createZip(key: String): Future[String] = { 
    val bucket = //get S3 bucket 
    val zipFileName = //name of zip file 
    val futureFile = bucket get key //Returns Future[BucketFile] 
    futureFile 
     .map(bucketFile => newZipFile(bucketFile.name, bucketFile.content) //Create zip file from original key 
     .map(newZipFile => bucket + newZipFile) //Does an S3 PUT of the zip file in the bucket and returns Unit 
     .map(unit => zipFileName) //Maps the returned unit to the zip file name once the zip file has been created and properly uploaded to S3 
} 

위에서 볼 수 있듯이이 메서드는 S3 키를 사용하여 만들어진 해당 zip 파일의 이름을 반환합니다.

S3 자격 증명에 권한이 없으므로 새 zip 파일을 넣은 두 번째 맵 메서드가 예외를 throw합니다. 문제 없습니다 - 어떻게 해결 해야할지 압니다.

문제는 REPL에서 모든 내용을 한줄 한줄 씩 실행하기 전까지는 이것이 사실이 아닌지 전혀 모른다는 것입니다. 즉,이 방법은 성공에 대해 거짓 긍정을 제공합니다.

나는 REPL에서 모든 방법을 실행

,이 얻을 :

scala> val a = createZip("test.zip") 
a: scala.concurrent.Future[String] = [email protected] 
scala> import scala.concurrent.Await 
Await.result(a, 120.seconds) 
scala> res1: String = "test.zip" 

결과는 Throwable (AN S3Exception FWIW)의 인스턴스 봤는데한다.

또한 onSuccessonFailure 콜백을 REPL에 적용하면 onSuccess이 발생합니다.

분명히, 나는 버킷 추가 호출에서 예외 발생을 삼키거나 숨기고 자합니다.

모든 오류가 공개되는지 확인하는 방법을 알고 싶습니다.

+0

아 ... 네 말이 맞아요. 나는 단지'flatMap'ed하고 REPL에서 예상되는 결과를 얻었습니다. 나는 컴파일러 또는 IDE가 타입 안전 위반에 대해 경고하지 않았지만 놀랍다. 나는 좀 더 가까이에서 일어나는 것을 생각할 필요가 있다고 생각한다. 어쨌든 귀하의 답변을 답변으로 남겨주세요. – Vidya

답변

1

bucket.add은 이고 Unit이 아닙니다. 이 라인에 그래서 :

.map(unit => zipFileName) 

당신은 실제로 당신이 응답 것을 던지는 것 같은 오류가, 길을 잃지 방법 인하는 StringFuture[Unit]을 매핑하고 있습니다. 이 map는 :

.map(newZipFile => bucket + newZipFile) 

flatMap가 제대로 Future[Future[Unit]]에서 Future[Unit]에 평평하게 될 것이다.

컴파일러가 Future[Unit] => B을 매핑하고 싶지 않다고 추측 할만큼 똑똑하지는 않지만 형식 주석을 추가하는 경우 컴파일이 실패합니다.

.map{unit: Unit => zipFileName} // Would complain the type is not Future[Unit] 
관련 문제