5

私は次の機能を持っています:

fun = function(expr) {
  mc = match.call()

  env = as.environment(within(
    list(),
    expr = eval(mc$expr)
  ))

  return(env)
}

これは 内で呼び出され、 内のtryCatch()エラー条件exprが適切に処理されるようにします。

標準のエラー状態で正常に動作します。

tryCatch({
  fun({
    stop('error')
  })
}, error = function(e) {
  message('error happened')
})

# error happened

ただし、期待エラーをキャプチャしませんtestthat(これは、私の特定のユース ケースに適しています)。

library(testthat)

tryCatch({
  fun({
    expect_true(FALSE)
  })
}, error = function(e) {
  message('expectation not met')
})

# Error: FALSE isn't true.

またはもっと簡単に:

library(testthat)

tryCatch({
  expect_true(FALSE)
}, error = function(e) {
  message('expectation not met')
})

# Error: FALSE isn't true.

予期エラーはキャッチされません。

この問題は、R 3.2.2 から R 3.3.0 にアップグレードした後に発生しました。つまり、期待エラーは R 3.2.2 で正確に検出されました。

R 3.3.0 にtestthat期待を寄せる方法はありますか?tryCatch()

4

1 に答える 1

9

デバッガーをオンに設定し、expect()数行のコードをステップ実行して (簡潔にするために出力を編集しました)、通知されている状態のクラスを調べました。

> debug(expect)
> xx = expect_true(FALSE)
...
Browse[2]> n
debug: exp <- as.expectation(exp, ..., srcref = srcref)
Browse[2]>
...
Browse[2]> class(exp)
[1] "expectation_failure" "expectation"         "condition"   
Browse[2]> Q
> undebug(expect)       

したがって、それはクラス「エラー」の状態ではなく、明示的にキャッチできます

> tryCatch(expect_true(FALSE), expectation_failure=conditionMessage)
[1] "FALSE isn't true.\n"

expectationクラスをキャッチすることもできます。

再起動すると、それが何らかの重要な場合に続行できます。

result <- withCallingHandlers({
    expect_true(FALSE)
    expect_true(!TRUE)
    expect_true("this sentence")
}, expectation_failure=function(e) {
    cat(conditionMessage(e))
    invokeRestart("continue_test")
})

出力あり

FALSE isn't true.
!TRUE isn't true.
"this sentence" isn't true.
> result
[1] FALSE

成功をキャッチまたは処理することもできます

> tryCatch(expect_true(TRUE), expectation_success=class)
[1] "expectation_success" "expectation"         "condition"  
于 2016-06-17T01:56:20.297 に答える