Implement proper script runtime exception rendering with tests
#KT-42335 fixed
This commit is contained in:
+44
@@ -0,0 +1,44 @@
|
||||
/*
|
||||
* Copyright 2010-2020 JetBrains s.r.o. and Kotlin Programming Language contributors.
|
||||
* Use of this source code is governed by the Apache 2.0 license that can be found in the license/LICENSE.txt file.
|
||||
*/
|
||||
|
||||
package kotlin.script.experimental.jvm.util
|
||||
|
||||
import java.io.PrintStream
|
||||
import kotlin.script.experimental.api.ResultValue
|
||||
|
||||
fun ResultValue.Error.renderError(stream: PrintStream) {
|
||||
var trace = error.stackTrace
|
||||
val wrappingTrace = wrappingException?.stackTrace
|
||||
if (wrappingException == null || trace.size < wrappingTrace!!.size) {
|
||||
error.printStackTrace(stream)
|
||||
} else {
|
||||
// subtracting wrapping message stacktrace from error stacktrace to show only user-specific part of it
|
||||
|
||||
fun PrintStream.printTrace(stackTrace: Array<StackTraceElement>, dropLastFrames: Int) {
|
||||
for (element in stackTrace.dropLast(dropLastFrames)) {
|
||||
println("\tat $element")
|
||||
}
|
||||
}
|
||||
|
||||
stream.println(error)
|
||||
stream.printTrace(trace, wrappingTrace.size)
|
||||
|
||||
var current: Throwable? = error.cause
|
||||
var wrapping = error
|
||||
val cyclesDetection = hashSetOf(wrapping)
|
||||
while (current != null && cyclesDetection.add(current)) {
|
||||
trace = current.stackTrace
|
||||
val sameFramesCount =
|
||||
trace.asList().asReversed().asSequence()
|
||||
.zip(wrapping.stackTrace.asList().asReversed().asSequence())
|
||||
.takeWhile { it.first == it.second }
|
||||
.count()
|
||||
stream.println("Caused by: $current")
|
||||
stream.printTrace(trace, sameFramesCount)
|
||||
wrapping = current
|
||||
current = current.cause
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user