You mean the line that did the actual throw error, or the whole "stack of lines" like so:
foo.swift:123
bar.swift:456
someFunction.swift:789
someLib.swift:111 // the line where `try someFunction()` is
To do that automatically swift would have to modify the "error" being returned (e.g. add a userValue dictionary key with, file/line info). Swift doesn't do this.
For you own app you can throw NSError and include the relevant file/line info as a userInfo key.
func makeError(... file: String = __FILE__, line: Int = __LINE__) -> Error {
let userInfo = ["errorFile": file, "errorLine": line]
let error = NSError(..., userInfo: userInfo)
return error
}
...
if ... {
throw makeError(...) // this file + line would be in the error
}
Is this for debugging during development or at runtime (e.g. to print to some log)?
For the former, you should be able to break on swift_willThrow in lldb.
For the latter, you use a wrapper error type and a helper function to wrap errors thrown from the functions you call:
struct SourceLocationError<T: Error>: Error {
let file: String, line: Int, error: T
}
func annotateError<T>(_ proc: @autoclosure () throws -> T, file: String = #file, line: Int = #line) throws -> T {
do {
return try proc()
} catch {
throw SourceLocationError(file: file, line: line, error: error)
}
}
And then use it like this:
do {
try annotateError(someFunction())
} catch {
print(error)
}
Sadly, from what I tried, pre-/postfix operators cant have extra arguments, even when they have default values. That would have made it a bit less visually obtrusive, but if that is an issue a shorter wrapper function name should go a long way.
Hi @2, A call stack would be nice, Although I don't mind just the file and line number @3, Yes it's for loggingز
All the ways shown here seems cool just except that I have to write an extra function for everything that errors, So I wonder if there's something easier?
I just want whenever I have an error raised I can log it in a way so I know where it happened, I rarely handle errors within the inner functions and just make it go to the highest function where main is because it works for my use case.