diff --git a/src/ScriptEngine/Machine/Contexts/ExceptionInfoContext.cs b/src/ScriptEngine/Machine/Contexts/ExceptionInfoContext.cs
index 869d6d408..30c9588df 100644
--- a/src/ScriptEngine/Machine/Contexts/ExceptionInfoContext.cs
+++ b/src/ScriptEngine/Machine/Contexts/ExceptionInfoContext.cs
@@ -33,10 +33,11 @@ public ExceptionInfoContext(ScriptException source) : base(ObjectType)
SetActualException(source);
}
- private ExceptionInfoContext(string message, IValue parameters) : base(ObjectType)
+ private ExceptionInfoContext(string message, IValue parameters, ExceptionInfoContext cause) : base(ObjectType)
{
Description = message;
Parameters = parameters;
+ _innerException = cause;
}
public bool IsErrorTemplate => _exc == null;
@@ -48,10 +49,11 @@ private void SetActualException(ScriptException exception)
if (exception is ParametrizedRuntimeException pre)
{
Parameters = pre.Parameter;
+ _innerException = pre.Cause;
}
}
- private ScriptException ActualException()
+ public ScriptException ActualException()
{
if (IsErrorTemplate)
{
@@ -147,8 +149,8 @@ public IValue InnerException
private IValue CreateInnerExceptionInfo()
{
- var exc = ActualException();
- if (exc.InnerException == null)
+ var exc = _exc;
+ if (exc?.InnerException == null)
return ValueFactory.Create();
var alreadyWrapped = ActualException() is ExternalSystemException;
@@ -193,11 +195,17 @@ public override string ToString()
return Description;
}
-
+ ///
+ ///
+ ///
+ /// Строка - Сообщение об ошибке
+ /// Произвольный - Дополнительная информация
+ /// ИнформацияОбОшибке - Причина, по которой произошло текущее исключение
+ ///
[ScriptConstructor(Name = "С возможностью передачи параметров")]
- public static ExceptionInfoContext Create(IValue msg, IValue parameter)
+ public static ExceptionInfoContext Create(IValue msg, IValue parameter, ExceptionInfoContext cause = null)
{
- return new ExceptionInfoContext(msg.AsString(), parameter);
+ return new ExceptionInfoContext(msg.AsString(), parameter, cause);
}
public static ExceptionInfoContext EmptyExceptionInfo()
diff --git a/src/ScriptEngine/Machine/ExceptionInfoFactory.cs b/src/ScriptEngine/Machine/ExceptionInfoFactory.cs
index 1afa05c39..51e8172bf 100644
--- a/src/ScriptEngine/Machine/ExceptionInfoFactory.cs
+++ b/src/ScriptEngine/Machine/ExceptionInfoFactory.cs
@@ -48,7 +48,7 @@ public Exception Raise(object raiseValue)
return raiseValue switch
{
ExceptionInfoContext { IsErrorTemplate: true } excInfo =>
- new ParametrizedRuntimeException(excInfo.Description, excInfo.Parameters),
+ new ParametrizedRuntimeException(excInfo.Description, excInfo.Parameters, excInfo.InnerException),
BslValue bslVal => new RuntimeException(bslVal.AsString()),
_ => new RuntimeException(raiseValue.ToString())
};
diff --git a/src/ScriptEngine/Machine/MachineInstance.cs b/src/ScriptEngine/Machine/MachineInstance.cs
index e342cf4aa..7f64884e9 100644
--- a/src/ScriptEngine/Machine/MachineInstance.cs
+++ b/src/ScriptEngine/Machine/MachineInstance.cs
@@ -1252,7 +1252,11 @@ private void RaiseException(int arg)
var exceptionValue = _operationStack.Pop().GetRawValue();
if (exceptionValue is ExceptionInfoContext { IsErrorTemplate: true } excInfo)
{
- throw new ParametrizedRuntimeException(excInfo.Description, excInfo.Parameters);
+ throw new ParametrizedRuntimeException(
+ excInfo.Description,
+ excInfo.Parameters,
+ excInfo.InnerException
+ );
}
else
{
diff --git a/src/ScriptEngine/Machine/ParametrizedRuntimeException.cs b/src/ScriptEngine/Machine/ParametrizedRuntimeException.cs
index 22f5e4e0b..097681de6 100644
--- a/src/ScriptEngine/Machine/ParametrizedRuntimeException.cs
+++ b/src/ScriptEngine/Machine/ParametrizedRuntimeException.cs
@@ -6,16 +6,19 @@ This Source Code Form is subject to the terms of the
----------------------------------------------------------*/
using OneScript.Exceptions;
+using ScriptEngine.Machine.Contexts;
namespace ScriptEngine.Machine
{
public class ParametrizedRuntimeException : RuntimeException
{
- public ParametrizedRuntimeException(string msg, IValue parameter) : base(msg)
+ public ParametrizedRuntimeException(string msg, IValue parameter, IValue cause = null) : base(msg)
{
Parameter = parameter;
+ Cause = cause;
}
public IValue Parameter { get; private set; }
+ public IValue Cause { get; private set; }
}
}
diff --git a/tests/global-funcs.os b/tests/global-funcs.os
index 50d9d4d37..a83cd129c 100644
--- a/tests/global-funcs.os
+++ b/tests/global-funcs.os
@@ -77,6 +77,7 @@
ВсеТесты.Добавить("Тест_ДолженПроверитьИнформацияОбОшибкеОписание");
ВсеТесты.Добавить("Тест_ДолженПроверитьКраткоеПредставлениеОшибки");
ВсеТесты.Добавить("Тест_ДолженПроверитьПодробноеПредставлениеОшибки");
+ ВсеТесты.Добавить("Тест_ДолженПроверитьИнформацияОбОшибкеСПричиной");
ВсеТесты.Добавить("Тест_ДолженПроверитьОбъединениеПутей");
@@ -888,6 +889,50 @@
ВызватьИсключение "Исключение не было брошено";
КонецПроцедуры
+Процедура Тест_ДолженПроверитьИнформацияОбОшибкеСПричиной() Экспорт
+
+ Попытка
+ ВыброситьТестовоеИсключение();
+ Исключение
+ ИнформацияОбОшибкеОригинальная = ИнформацияОбОшибке();
+ КонецПопытки;
+
+ юТест.ПроверитьИстину(ЗначениеЗаполнено(ИнформацияОбОшибкеОригинальная), "Исключение не было брошено");
+
+ Объект = Новый ИнформацияОбОшибке("Я новая ошибка", Новый Массив, ИнформацияОбОшибкеОригинальная);
+
+ Попытка
+ ВызватьИсключение Объект;
+ Исключение
+ ИнформацияОбОшибке = ИнформацияОбОшибке();
+
+ юТест.ПроверитьИстину(
+ СтрНайти(ИнформацияОбОшибке.Описание, "Я новая ошибка") > 0,
+ "Описание в новой информации об ошибке должно быть текстом из конструктора"
+ );
+
+ юТест.ПроверитьТип(
+ ИнформацияОбОшибке.Причина,
+ "ИнформацияОбОшибке",
+ "У информации об ошибке которому передали причину в конструкторе,
+ |должна быть заполнена причина после выброса исключения"
+ );
+
+ юТест.ПроверитьРавенство(
+ ИнформацияОбОшибке.Причина,
+ ИнформацияОбОшибкеОригинальная,
+ "Причина в новой информации об ошибке должна соответствовать переданной в конструктор"
+ );
+
+ юТест.ПроверитьИстину(
+ СтрНайти(ИнформацияОбОшибке.Причина.Описание, "тест-тест-тест") > 0,
+ "Оригинальное сообщение должно содержать текст исключения"
+ );
+
+ КонецПопытки;
+
+КонецПроцедуры
+
Процедура Тест_ДолженПроверитьОбъединениеПутей() Экспорт
СИ = Новый СистемнаяИнформация();
Если Найти(СИ.ВерсияОС,"Windows") > 0 Тогда