Многие при работе с корпоративным порталом (Enterprise Portal) в Microsoft Axapta сталкиваются с ошибкой 'Недопустимый диапазон'. В этом совете рассказано как бороться с этой ошибкой.
На скриншоте справа показана эта ошибка. Появляется она, как правило, если в коде записи, которую должен показать корпоративный портал, содержатся русские буквы (или другие неASCII символы).
В чем причина?
Любое веб-приложение всю информацию может передать только в адресной строке. Причина ошибки кроется в том, как корпоративный портал передает информацию о записи, которую надо отобразить.
Если свойствах таблицы указано, что индекс по RecID не нужен, то Аксапта берет первый попавшийся уникальный индекс и составляет адрес записи следующим образом WKEY=[fieldId1,fieldValue1][fieldId2,fieldValue2]... Где fieldId1, fieldId2 и т.д. - поля, входящие в уникальный индекс отображаемой таблицы. А fieldValue1, fieldValue2 и т.д. - значения этих полей соответственно.
Если в таблице есть индекс по RecId, то в адресной строке в параметре WKEY передается RecID. На картинке ниже recid = 8520336. А код поля RecID = 65534 (-1).

Обратите внимание: если в таблице нет уникального индекса, то Аксапта берет первый попавшийся индекс и к списку полей добавляет recId. Смотрите метод Global::record2DynaKey() для того, чтобы узнать детали.
При создании параметра WKEY для таблиц без индекса RecID и возникает проблема. Дело в том, что символы кирилицы в адресной строке могут быть закодированы при помощи "безопасного" набора символов из ASCII-таблицы.
Аксапта использует метод iisServer.htmlEncode() для кодирования в безопасный набор символов. Этот метод находится в ядре и недоступен программисту. В этом методе и происходит ошибка. Вместо кодирования в %-стиле, метод кодирует в стиле html-кода. Например, буква Г кодируется как Г.
Взглянем поподробнее на адресную строку страницы, в которой возникла ошибка.

Та-да-а-ам! Вот оно!
Во-первых, правильно закодирован только первый символ (обратите внимание, у второго и следующих не хватает #). А во-вторых, и это самое главное, символ & является разделителем между параметрами в адресной строке. А это значит, параметр WKEY получит значение "[1:", когда IIS получит и разберет строку. Именно поэтому Аксапта и ругается на недопустимый диапазон.
Что делать?
Есть два способа. И оба способа требуют средств разработки.
Способ 1
В таблицах, по которым ругается корпоративный портал, создайте индекс по recId. Для этого установите у свойства таблицы CreateRecIdIndex значение Yes.
Код таблицы можно узнать, если посмотреть в адресной строке на параметр WTID (в нашем примере это таблица с номером 103) и воспользоваться небольшим Job'ом:
static void mazTableName(Args _args) { ; info(new dicttable(103).name()); }
Спасибо Андрею Васько и Вадиму Гончаренко за предложенный способ.
Способ 2
Из соображений производительности не всегда желательно создавать новый индекс. Кроме того, бывают случаи, когда создание индекса по RecId просто невозможно. В таких случаях можно подправить код, где выполняется кодирование адреса. В методе WebLink::url найдите строчку, в которой вызывается iisServer.htmlEncode.

Либо вообще уберите вызов этого метода, либо замените на вызов своего кодировщика. Для целей тестирования вполне достаточно просто убрать кодирование в безопасный набор. В большинстве случаев, пользователи не используют спецсимволы (<, ", &, >), а современные браузеры нормально работают с Unicode-символами.
Однако, в боевых условиях отсутствие кодировщика означает дыру в безопасности. Конечно, вставить опасный код в 10-20 символов кода очень сложно. Однако не завбывайте, что бывают таблицы, где в уникальный индекс входит наименование. А туда уже вполне вставить очень даже зловредный код. Поэтому в боевых условиях кодирование в безопаснй набор обязательно.
Буду рад Вашим замечаниям и предложениям.
mazzy@mazzy.ru, Мазуркин Сергей