這篇來介紹的是在 Effect 裡面怎麼寫 log ,不知道各位平常有沒有習慣在寫 log ,如果程式有 log 的話,可以幫助我們了解程式現在的狀態,在除錯上會很有幫助。如果有在寫 log 可能會知道像是 pino 或是像 winston 這樣的 logging 套件,那 Effect 的 logging 又跟這些既有的套件有什麼差別呢?我們來看下去
Effect 已經內建了 log 的機制,你只需要呼叫 Effect.log
或是同系列的 function ,就會可以紀錄 log 了
pipe(
Effect.gen(function*() {
yield* Effect.log("log")
yield* Effect.logInfo("logInfo")
// 還記得之前提過 Cause 這個 Effect 用來完整表達錯誤類型的型態嗎?
// 如果這邊直接傳入 Error 反而不會正常顯示
yield* Effect.logError("logError", Cause.fail(new Error("oh no")))
}),
Effect.runPromise
)
而以上的程式會顯示
timestamp=2025-10-07T11:46:57.679Z level=INFO fiber=#0 message=log
timestamp=2025-10-07T11:46:57.680Z level=INFO fiber=#0 message=logInfo
timestamp=2025-10-07T11:46:57.680Z level=ERROR fiber=#0 message=logError cause="Error: oh no
at eval (/home/r24e23sdiw9w1oqo1ljpo851jbidnw-h5th/playground/dist/main.js:7:69)
at eval (/home/r24e23sdiw9w1oqo1ljpo851jbidnw-h5th/playground/node_modules/.pnpm/effect@3.17.14/node_modules/effect/dist/cjs/internal/fiberRuntime.js:129:77)"
在 pino 裡有個很方便的功能是你可以把一個 object 傳入第一個參數,例如
pino.info({ request }, 'receieve request')
這樣你就會在 log 中看到 request 的詳細內容,在 Effect 中要達成類似的效果,需要使用 Effect.annotateLogs
:
pipe(
Effect.gen(function*() {
yield* Effect.log("log")
}),
// 這樣上面的 Effect 中的所有 log ,包含 Effect 中的 Effect 中的 log 都會有同樣的資料
Effect.annotateLogs({
foo: "bar"
}),
Effect.runPromise
)
上面的輸出是:
timestamp=2025-10-07T12:05:36.292Z level=INFO fiber=#0 message=log foo=bar
我們一個 Effect 代表著一個任務,如果我們想要測量一下完成一個任務花了多少時間,我們不用再自己計算 Date.now() - start
了,我們只需要 Effect.withLogSpan
pipe(
Effect.gen(function*() {
yield* Effect.log('first')
yield* Effect.sleep('500 millis')
yield* Effect.log('second')
yield* Effect.sleep('500 millis')
yield* Effect.log('done')
}),
// 你可以幫你計時的區塊取個名字,這代表你可以計時多個區塊
Effect.withLogSpan('span'),
Effect.runPromise
)
上面在每次 log 的同時就會輸出時間了
timestamp=2025-10-07T12:20:32.207Z level=INFO fiber=#0 message=first span=0ms
timestamp=2025-10-07T12:20:32.718Z level=INFO fiber=#0 message=second span=511ms
timestamp=2025-10-07T12:20:33.225Z level=INFO fiber=#0 message=done span=1018ms
以上簡單的介紹了一個使用方法還有 Effect logging 的特點。而 Effect logging 跟 pino 還有 winstion 這些套件比起來, Effect 有著以下的優勢:
但缺點其實也挺明顯的
這篇主要是介紹基本的 logging 的使用, Effect 很大的善用了自己主要的流程管理功能來增強 logging ,比如計時跟 annotate 資料在所有的 log 上,不過在 log error 上就稍微不便。如果你的程式已經在用 Effect 了,整體而言還是很推薦使用內建的 logging,特別是下一篇要來看 Effect 的 observability 的整合,絕對是值得使用的