fix: accept comprehension-required tag variants everywhere (v3.6.40)
The TERMINAL PROFILE chain parsed the SET UP MENU title with 'tag == 0x05' only, so the live Alfa card's title (CR-set 0x85, 'Alfa Mobile') was dropped: /api/menu returned items without a title and the PWA showed 'No menu set by the card' - card-specific only because cards pick the tag variant (this one sends plain 0x8F items and a CR-set title in the same command). - _parse_setup_menu_command (pure, tested with the live FETCH bytes) replaces the inline parse; the PWA shows a title-less menu as 'STK: Menu' instead of 'No menu set by the card' (stkMenuLabel, pure). - _cmd_tlv is now the single lookup helper: exact tag, then tag ^ 0x80 (bit 8 is the CR flag, TS 101 220 7.1.1); the old '| 0x80'-only helper and the duplicate _cmd_tlv_any are gone. - Remaining single-style checks fixed: _parse_setup_menu_items (0x8F/0x0F), _parse_select_item title (0x85/0x05), _find_sms_tpdu (0x8B/0x0B - the plain variant lost the SEND SHORT MESSAGE PoR TPDU), the response scripting parsers (R-APDU 0x23/0xA3, executed count 0x80/0x00) and the FF21 resource tags (0x81-0x83/0x01-0x03). - tests/test_tag_variants.py flips the CR flag on every top-level tag of real command fixtures and asserts identical parse results for all parsers (verified to fail when a single-style lookup is reintroduced). sw cache simple-v313; tests: 524 Python / 675 Node.
This commit is contained in:
@@ -488,7 +488,7 @@
|
||||
<p class="text-sm mb-3">Работа с сессией Card Application Toolkit. Четыре подвкладки: <strong>«Телефон»</strong> (меню STK, STATUS и опрос, подписанные события, журнал проактивных команд), <strong>«Конфигурация TR»</strong> (данные ответов, подставляемые в TERMINAL RESPONSE для проактивных команд), <strong>«eSIM LPA»</strong> (локальные операции с eUICC) и <strong>«Тест-скрипт»</strong> (сценарные тест-скрипты карты с ожиданием проактивных команд, см. <a href="#test-script" class="text-blue-600 dark:text-blue-400 hover:underline">§8.9</a>).</p>
|
||||
|
||||
<h3 id="stk-menu" class="text-lg font-medium mb-2">8.1 Меню STK</h3>
|
||||
<p class="text-sm mb-3">Если карта выдала команду SET UP MENU, вверху этого представления появляется блок «Меню STK» с изумрудной кнопкой <strong>STK: <название></strong>, открывающей оверлей меню (браузер STK-меню карты). Если карта не задала меню, вместо кнопки показывается «Меню не задано картой». Состояние меню обновляется при каждом открытии представления. Пункты меню, для которых карта передала <strong>Next Action Indicator</strong> (TS 102 223 §8.24), показывают его серым суффиксом (например, <code class="font-mono text-sm">→ SET UP MENU</code>) — что карта выполнит при выборе пункта. Интерактивные проактивные команды всегда получают TERMINAL RESPONSE: оверлей ждёт вашего выбора, и если вы не ответили и не нажали <strong>Timeout</strong>, сервер сам отвечает результатом timeout через <code class="font-mono text-sm">--menu-timeout</code> секунд (по умолчанию 60, <code class="font-mono text-sm">0</code> отключает). <strong>Назад</strong> и <strong>Timeout</strong> продолжают диалог с картой: если карта в ответ выдаёт следующую проактивную команду (SELECT ITEM или DISPLAY TEXT), панель показывает её; кэшированное верхнее меню появляется только когда карте больше нечего выполнять. Оверлей также отвечает на запросы карты <strong>GET INKEY</strong> и <strong>GET INPUT</strong> (TS 102 223 §6.4.2/§6.4.3): панель показывает текст карты и поле ввода, ограничения которого заданы командой (длина ответа min–max, цифровая клавиатура, скрытый ввод, подставленный текст по умолчанию, кнопки Да/Нет для GET INKEY, справка, если карта её объявила), а ответ возвращается в Text string внутри TERMINAL RESPONSE в запрошенной кодировке (SMS-алфавит unpacked, UCS2 или packed).</p>
|
||||
<p class="text-sm mb-3">Если карта выдала команду SET UP MENU, вверху этого представления появляется блок «Меню STK» с изумрудной кнопкой <strong>STK: <название></strong>, открывающей оверлей меню (браузер STK-меню карты). Если карта не задала меню, вместо кнопки показывается «Меню не задано картой»; SET UP MENU без заголовка (alpha identifier необязателен) показывается как <strong>STK: Меню</strong>. Состояние меню обновляется при каждом открытии представления. Пункты меню, для которых карта передала <strong>Next Action Indicator</strong> (TS 102 223 §8.24), показывают его серым суффиксом (например, <code class="font-mono text-sm">→ SET UP MENU</code>) — что карта выполнит при выборе пункта. Интерактивные проактивные команды всегда получают TERMINAL RESPONSE: оверлей ждёт вашего выбора, и если вы не ответили и не нажали <strong>Timeout</strong>, сервер сам отвечает результатом timeout через <code class="font-mono text-sm">--menu-timeout</code> секунд (по умолчанию 60, <code class="font-mono text-sm">0</code> отключает). <strong>Назад</strong> и <strong>Timeout</strong> продолжают диалог с картой: если карта в ответ выдаёт следующую проактивную команду (SELECT ITEM или DISPLAY TEXT), панель показывает её; кэшированное верхнее меню появляется только когда карте больше нечего выполнять. Оверлей также отвечает на запросы карты <strong>GET INKEY</strong> и <strong>GET INPUT</strong> (TS 102 223 §6.4.2/§6.4.3): панель показывает текст карты и поле ввода, ограничения которого заданы командой (длина ответа min–max, цифровая клавиатура, скрытый ввод, подставленный текст по умолчанию, кнопки Да/Нет для GET INKEY, справка, если карта её объявила), а ответ возвращается в Text string внутри TERMINAL RESPONSE в запрошенной кодировке (SMS-алфавит unpacked, UCS2 или packed).</p>
|
||||
|
||||
<h3 id="subscribed-events" class="text-lg font-medium mb-2">8.2 Подписанные события (SET UP EVENT LIST)</h3>
|
||||
<p class="text-sm mb-2">События, которые отслеживает карта. У каждого события есть кнопка <strong>Отправить</strong>, открывающая форму, специфичную для типа события:</p>
|
||||
|
||||
+1
-1
@@ -487,7 +487,7 @@
|
||||
<p class="text-sm mb-3">Interacts with the Card Application Toolkit session. The view has four pills: <strong>Phone</strong> (STK menu, STATUS and polling, subscribed events, proactive command log), <strong>TR Config</strong> (response data injected into TERMINAL RESPONSEs for proactive commands), <strong>eSIM LPA</strong> (local eUICC operations) and <strong>Test script</strong> (scripted card test scripts with proactive-command expectations, see <a href="#test-script" class="text-blue-600 dark:text-blue-400 hover:underline">§8.9</a>).</p>
|
||||
|
||||
<h3 id="stk-menu" class="text-lg font-medium mb-2">8.1 STK menu</h3>
|
||||
<p class="text-sm mb-3">When the card has issued a SET UP MENU command, a “STK menu” block appears at the top of this view with an emerald <strong>STK: <title></strong> button that opens the menu overlay (same as the card’s STK menu browser). If the card has not set up a menu, the block shows “No menu set by the card” instead. The menu state is refreshed each time the view is opened. Menu items whose card-provided <strong>Next Action Indicator</strong> (TS 102 223 §8.24) is present show it as a small gray suffix (e.g. <code class="font-mono text-sm">→ SET UP MENU</code>) — what the card would do when the item is selected. User-interactive proactive commands always get a TERMINAL RESPONSE: the overlay pauses for your choice, and if you neither answer nor press <strong>Timeout</strong>, the server answers with a timeout result after the <code class="font-mono text-sm">--menu-timeout</code> seconds (default 60, <code class="font-mono text-sm">0</code> disables). <strong>Back</strong> and <strong>Timeout</strong> keep the dialogue with the card going: when the card replies with a further proactive command (SELECT ITEM or DISPLAY TEXT) the panel shows it; the cached top menu appears only when the card has nothing more to execute. The overlay also answers the card’s <strong>GET INKEY</strong> and <strong>GET INPUT</strong> prompts (TS 102 223 §6.4.2/§6.4.3): the panel shows the card’s text with an input field whose constraints come from the command (Response length min–max, digits-only keyboard, hidden entry, default text prefilled, Yes/No buttons for GET INKEY, help when the card advertises it), and the answer is returned in the TERMINAL RESPONSE’s Text string in the requested coding (SMS default alphabet unpacked, UCS2 or packed).</p>
|
||||
<p class="text-sm mb-3">When the card has issued a SET UP MENU command, a “STK menu” block appears at the top of this view with an emerald <strong>STK: <title></strong> button that opens the menu overlay (same as the card’s STK menu browser). If the card has not set up a menu, the block shows “No menu set by the card” instead; a SET UP MENU without a title (the alpha identifier is optional) shows as <strong>STK: Menu</strong>. The menu state is refreshed each time the view is opened. Menu items whose card-provided <strong>Next Action Indicator</strong> (TS 102 223 §8.24) is present show it as a small gray suffix (e.g. <code class="font-mono text-sm">→ SET UP MENU</code>) — what the card would do when the item is selected. User-interactive proactive commands always get a TERMINAL RESPONSE: the overlay pauses for your choice, and if you neither answer nor press <strong>Timeout</strong>, the server answers with a timeout result after the <code class="font-mono text-sm">--menu-timeout</code> seconds (default 60, <code class="font-mono text-sm">0</code> disables). <strong>Back</strong> and <strong>Timeout</strong> keep the dialogue with the card going: when the card replies with a further proactive command (SELECT ITEM or DISPLAY TEXT) the panel shows it; the cached top menu appears only when the card has nothing more to execute. The overlay also answers the card’s <strong>GET INKEY</strong> and <strong>GET INPUT</strong> prompts (TS 102 223 §6.4.2/§6.4.3): the panel shows the card’s text with an input field whose constraints come from the command (Response length min–max, digits-only keyboard, hidden entry, default text prefilled, Yes/No buttons for GET INKEY, help when the card advertises it), and the answer is returned in the TERMINAL RESPONSE’s Text string in the requested coding (SMS default alphabet unpacked, UCS2 or packed).</p>
|
||||
|
||||
<h3 id="subscribed-events" class="text-lg font-medium mb-2">8.2 Subscribed events (SET UP EVENT LIST)</h3>
|
||||
<p class="text-sm mb-2">The events the card monitors. Each event has a <strong>Send</strong> button that opens a form specific to the event type:</p>
|
||||
|
||||
+14
-3
@@ -1732,7 +1732,7 @@
|
||||
// ===== Version =====
|
||||
// Single source of truth for the PWA version: shown in the header and used
|
||||
// by the server version check in pysimConnect().
|
||||
const SIMPLE_VERSION = '3.6.39';
|
||||
const SIMPLE_VERSION = '3.6.40';
|
||||
document.getElementById('app-version').textContent = 'v' + SIMPLE_VERSION;
|
||||
|
||||
// ===== Tab switching =====
|
||||
@@ -9599,13 +9599,23 @@ async function ramExecute() {
|
||||
// ===== STK Menu Browser =====
|
||||
let stkMenuStack = [];
|
||||
|
||||
// The STK button label from /api/menu (pure): the card's title, or a generic
|
||||
// label when the SET UP MENU carried none (the alpha identifier is optional,
|
||||
// TS 102 223 6.6.7 - a title-less menu must not read as "No menu set by the
|
||||
// card"). Empty string = no menu.
|
||||
function stkMenuLabel(data) {
|
||||
if (!data || !data.items || !data.items.length) return '';
|
||||
return data.title || t('Menu');
|
||||
}
|
||||
|
||||
async function stkCheckMenu() {
|
||||
try {
|
||||
const data = await pysimFetch('/api/menu');
|
||||
const btn = document.getElementById('stk-menu-btn');
|
||||
const none = document.getElementById('stk-menu-none');
|
||||
if (data && data.title && data.items && data.items.length) {
|
||||
document.getElementById('stk-menu-title').textContent = data.title;
|
||||
const label = stkMenuLabel(data);
|
||||
if (label) {
|
||||
document.getElementById('stk-menu-title').textContent = label;
|
||||
btn.style.display = '';
|
||||
none.style.display = 'none';
|
||||
} else {
|
||||
@@ -17641,6 +17651,7 @@ const LANG_RU = {
|
||||
'Yes': 'Да',
|
||||
'No': 'Нет',
|
||||
'Help': 'Справка',
|
||||
'Menu': 'Меню',
|
||||
'one character': 'один символ',
|
||||
'characters': 'символов',
|
||||
'up to': 'до',
|
||||
|
||||
+1
-1
@@ -1,4 +1,4 @@
|
||||
const CACHE = 'simple-v312';
|
||||
const CACHE = 'simple-v313';
|
||||
const URLS = [
|
||||
'index.html',
|
||||
'help.html',
|
||||
|
||||
@@ -26,6 +26,7 @@ code += extractFunc(html, 'stkNoPendingError') + '\n';
|
||||
code += extractFunc(html, 'stkMenuPanelReset') + '\n';
|
||||
code += extractFunc(html, 'stkMenuNaiSuffix') + '\n';
|
||||
code += extractFunc(html, 'stkMenuItemsHtml') + '\n';
|
||||
code += extractFunc(html, 'stkMenuLabel') + '\n';
|
||||
code += extractFunc(html, 'stkInputHtml') + '\n';
|
||||
code += extractFunc(html, 'stkInputHint') + '\n';
|
||||
code += extractFunc(html, 'stkInputValidate') + '\n';
|
||||
@@ -181,3 +182,15 @@ test('stkInputValidate mirrors the server input rules', () => {
|
||||
assert.strictEqual(stkInputValidate({ type: 'get_inkey', digits_only: true }, '*').ok, true);
|
||||
assert.strictEqual(stkInputValidate({ type: 'get_inkey', digits_only: true }, 'a').ok, false);
|
||||
});
|
||||
|
||||
test('stkMenuLabel shows the card title or a generic label', () => {
|
||||
globalThis.t = s => s;
|
||||
// the card's title when it sent one
|
||||
assert.strictEqual(stkMenuLabel({ title: 'Alfa Mobile', items: [{ id: 1 }] }), 'Alfa Mobile');
|
||||
// a title-less SET UP MENU still shows the menu (TS 102 223 6.6.7)
|
||||
assert.strictEqual(stkMenuLabel({ items: [{ id: 1 }] }), 'Menu');
|
||||
// no items = no menu, whatever the title
|
||||
assert.strictEqual(stkMenuLabel({ title: 'x', items: [] }), '');
|
||||
assert.strictEqual(stkMenuLabel({ items: [] }), '');
|
||||
assert.strictEqual(stkMenuLabel(null), '');
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user