I’m trying to use theException.CallStack()
to print a Java-like stack trace when script caught any exceptions.
I ran
put keys of item 1 of theException.CallStack()
and got
["Handler","HandlerOffset","Line","MeObjectID","MessageName","MessageType","objectType","RepeatIndex","ScriptLine","ScriptObjectID","TargetObjectID","TryDepth"]
Most of them are intuitive, but have some questions. I looked up the documentation of the CallStack
function, but there were no explanation of the properties.
- What does
HandlerOffset
mean? I see some large numbers like 21541 or 18755.
- Is
Line
different from ScriptLine
?
MeObjectID
, ScriptObjectID
and TargetObjectID
seem to have the same value. Is this expected?
HandlerOffset
is the offset from the beginning of the script to the beginning of that handler. So a HandlerOffset of 21541 indicates that the handler begins at the 21,541st character of the script.
SenseTalk normally counts lines within each handler, so Line
is the handler line number. For convenience when working with editors that show a text line number, we recently added ScriptLine
as well which is the line number within the script as a whole.
MeObjectID
, ScriptObjectID
and TargetObjectID
are most often all the same, but can be different if the message was sent to a different target object than the script, or if the script is helping another object. See the documentation on Objects and Messages for more details: Objects and Messages | EPF Docs
Hi, @SenseTalkDoug , thanks for the explanation.
As for HandlerOffset
, I guessed that was something like that, but I was confused because it was slightly off when opening the script in a text editor. It appears the number does not count the Windows line ending characters (CR-LF) correctly. For example, I had a handler at line 54 of a script and the HandlerOffset
was showing 1713, but the actual position was 1764th character (=1713+54) within the script file. Anyway, I don’t need to use it for now, but good to know.
Here is the Java-like stack trace printing snippet I came up with:
Try
(* code that may throw exceptions *)
Catch theException
Set printableStackTrace to theException.asText
Set stacks to theException.CallStack
Repeat with each item stack of stacks reversed
If stack.RepeatIndex > 0
Set stackInfo to Merge("[[newline]] at [[stack.MeObjectID]]:[[stack.Handler]]:[[stack.Line]] (line [[stack.ScriptLine]]) x[[stack.RepeatIndex]]")
Else
Set stackInfo to Merge("[[newline]] at [[stack.MeObjectID]]:[[stack.Handler]]:[[stack.Line]] (line [[stack.ScriptLine]])")
End if
Put stackInfo after printableStackTrace
End repeat
LogError printableStackTrace
Throw theException
End if
Interesting point. SenseTalk converts scripts internally to use standard (LF only) line endings. Hence the discrepancy in the HandlerOffset when you use Windows line endings.
Thanks for sharing your code. It’s helpful to see how you are using it, and other people may find it useful. I would suggest using ScriptObjectID rather than MeObjectID, though. In cases where they are different, ScriptObjectID will always identify the script code that is running, and MeObjectID will be some other object that is being helped by this script.
Thanks for your valuable suggestion. I changed my code to use ScriptObjectID.