In 2018, I wrote the blog post Throwing managed exceptions from X++ in D365FO, where I pondered upon how throwing proper exceptions objects in X++ would be beneficial. This is still true. I also showed a proof of concept how it can be done despite the fact that X++ doesn’t directly support it. But this has changed! Platform Update 31 has introduced the possibility to throw managed (CLR) exceptions directly with the throw statement.
Therefore you can now do things like this right from X++:
throw new System.ArgumentException('A value must be set', 'FromDate');
Then you can react to this particular type of exception and you’ll also get a lot of context, such as which argument is wrong. For example:
warning(strFmt("Please provide a valid value for the parameter '%1'.", argEx.ParamName));
If you want to define your own exception class (e.g. FieldEmptyException from my previous blog post), you still can’t do it in X++ – you need a C# project or something. And it’s probably not going to change. But it shouldn’t be a big problem, because working with C# projects in D365FO is very easy.
PU31 added one more ability of throw. Imagine that you want to log an exception, but you don’t want to handle it. You catch it, log it and then you can throw another exception. But this new exception won’t have the same properties as the original one, e.g. its stack trace will show that it was thrown from your catch clause. To rethrow the same exception, use throw without any argument. Like this: