Короткий ответ.
error_marshaling_enabled
опция влияет только на то, как объекты ошибок кодируются в теле ответа (48, IPROTO_DATA). Это не влияет на то, как они возвращаются как исключения в заголовке ответа (82, IPROTO_ERROR).
Длинный ответ.
В Tarantool объект ошибки можно вернуть двумя способами: как исключение и как объект. Например, вот как вызвать ошибку как исключение:
function throw_error()
box.error({code = 1000, reason = "Error message"})
-- Or
error('Some error string')
end
Вот как вернуть его как объект:
function return_error()
return box.error.new({code = 1000, reason = "Error message"})
end
Если функция была вызвана удаленно, с использованием IPROTO протокол через соединитель, такой как netbox, или соединитель PHP, или любой другой, способ возврата ошибки влияет на то, как она кодируется в ответном пакете MessagePack. Когда функция выдает ошибку, и ошибка достигает верхнего кадра стека, не будучи обнаруженной, она кодируется как IPROTO_ERROR (82) и IPROTO_ERROR_24 (49).
Когда объект ошибки возвращается как обычное значение, а не как исключение, оно также кодируется как обычное значение внутри IPROTO_DATA (48). Так же, как строка, число, кортеж и т. Д. c.
С кодировкой IPROTO_ERROR / IPROTO_ERROR_24 не так много места для конфигурации. Формат этих значений изменить нельзя. IPROTO_ERROR всегда возвращается как карта MessagePack со стеком ошибок. IPROTO_ERROR_24 всегда является сообщением об ошибке. Поле IPROTO_ERROR_24 сохранено для совместимости с коннекторами к версиям Tarantool <2.4.1. </p>
С кодировкой в составе IPROTO_DATA вы можете выбрать способ сериализации с помощью опции error_marshaling_enabled
. Если это правда, ошибки кодируются как тип расширения MessagePack MP_EXT и содержат весь стек ошибок, закодированный точно так же, как значение IPROTO_ERROR. Если для параметра установлено значение false (поведение по умолчанию в 2.4.1), ошибка кодируется в виде строки MP_STR, которая является сообщением об ошибке. Если имеется стек ошибок, кодируется только самая новая ошибка.
error_marshaling_enabled
существует для обратной совместимости, на случай, если ваше приложение в Tarantool хочет быть совместимым со старыми коннекторами, которые не поддерживают MP_EXT закодированные ошибки.
В Tarantool <2.4.1 ошибки кодировались в результате MessagePack в виде строки с сообщением об ошибке, а стеки ошибок вообще не существовали. Поэтому, когда были представлены новый формат и функция стеков ошибок, установка нового формата по умолчанию было бы слишком радикальным изменением, нарушающим старые соединители. </p>
Рассмотрим эти примеры того, как маршалинг ошибок влияет на результаты. Здесь я использую консоль Tarantool 2.4.1 и встроенный коннектор netbox. Приведенный ниже код можно скопировать и вставить в консоль.
Первый экземпляр:
box.cfg{listen = 3313}
box.schema.user.grant('guest', 'super')
function throw_error()
box.error({code = 1000, reason = "Error message"})
end
function return_error()
return box.error.new({code = 1000, reason = "Error message"})
end
Второй экземпляр:
netbox = require('net.box')
c = netbox.connect(3313)
Теперь я пытаюсь вызвать функцию на второй экземпляр:
tarantool> c:call('throw_error')
---
- error: Error message
...
c:call('throw_error')
вызвал исключение. Если я поймаю его с помощью функции pcall()
Lua, я увижу объект ошибки.
tarantool> ok, err = pcall(c.call, c, 'throw_error')
tarantool> err:unpack()
---
- code: 1000
base_type: ClientError
type: ClientError
message: Error message
trace:
- file: '[string "function throw_error()..."]'
line: 2
...
Как видите, я не устанавливал error_marshaling_enabled
, но получил полную ошибку. Теперь я вызову другую функцию без исключений. Но объект ошибки не будет заполнен.
tarantool> err = c:call('return_error')
tarantool> err
---
- Error message
...
tarantool> err:unpack()
---
- error: '[string "return err:unpack()"]:1: attempt to call method ''unpack'' (a nil
value)'
...
Ошибка была возвращена в виде простой строки, сообщения об ошибке. Не как объект ошибки. Теперь я включу маршалинг:
tarantool> c:eval('box.session.settings.error_marshaling_enabled = true')
---
...
tarantool> err = c:call('return_error')
---
...
tarantool> err:unpack()
---
- code: 1000
base_type: ClientError
type: ClientError
message: Error message
trace:
- file: '[C]'
line: 4294967295
...
Теперь та же функция вернула ошибку в новом формате, более функциональном.
В итоге: error_marshaling_enabled
влияет только на возвращаемые ошибки. Не выкидываемые ошибки.