feat: Test script pill in the Phone simulator (v3.5.11)

- Phone simulator tab: a fourth pill **Test script** - script list
  (localStorage `simple_tests`) with New/Clone/Delete/Export/Import, a
  form-based step editor (modal) and a run panel.
- Actions: ENVELOPE (Event Download), Menu Selection, UPDATE/READ file by
  path, raw APDU, SCP80 (C-APDU or a pre-built packet, per-step TAR/SPI1/
  SPI2 overrides; the preset is matched by the equipped card's ICCID and
  the final counter is written back) and STATUS with an optional poll.
  Every action has SW/data checks (exact or ?-mask) and a PoR check for
  SCP80, with an error (stops) / warning (continues) fail level.
- Expectations: FETCH the command announced by the previous step, verify
  type/qualifier/text/item/raw and answer with the scripted TERMINAL
  RESPONSE (result, item id, text, extra TLVs); templates for STK menu
  browsing and an applet via SCP80.
- Run panel: progress banner (plus a marker on the pill), per-step
  OK/Warning/Error badges with expected vs actual values, sent/received
  hex, decoded commands and the SCP80 counter; 500 ms polling while a run
  is active, and a running script disables other card controls
  (data-needs gate; the server answers 409 to other card endpoints).
- Help EN/RU (8.9 Test script), AGENTS; version 3.5.11; sw simple-v264.

579 frontend / 467 Python green.
This commit is contained in:
2026-09-27 01:19:32 +03:00
parent 3a4a098f1a
commit 722e237ea4
9 changed files with 1089 additions and 7 deletions
+9
View File
@@ -544,6 +544,15 @@
</section>
<section class="mb-10">
<h3 id="test-script" class="text-lg font-medium mb-2">8.9 Тест-скрипт</h3>
<p class="text-sm mb-2"><strong>Тест-скрипт</strong> &mdash; упорядоченный список <strong>действий</strong> и <strong>ожиданий</strong> проактивных команд, выполняемый на подключённой карте на стороне сервера. Пока запуск активен, карта принадлежит скрипту: остальные операции с картой отклоняются (HTTP&nbsp;409), фоновый опрос STATUS приостанавливается; отчёт о запуске хранится в памяти (в том числе после перезагрузки страницы) до нажатия <strong>Очистить отчёт</strong>. Скрипты хранятся в localStorage (<code class="font-mono text-sm">simple_tests</code>) и экспортируются/импортируются как JSON.</p>
<ul class="list-disc list-inside text-sm space-y-1 mb-3">
<li><strong>Действия</strong> &mdash; <em>Envelope</em> (Event Download: тип события + данные), <em>Menu Selection</em> (item id 1&ndash;255), <em>UPDATE/READ файла</em> (путь + режим; чтение проверяет данные файла), <em>сырой APDU</em> (без авто-обработчика), <em>SCP80</em> (C-APDU или готовый защищённый пакет, опциональные переопределения TAR/SPI1/SPI2; KIc/KID и счётчик берутся из пресета карты, подобранного по ICCID подключённой карты, а счётчик записывается обратно после запуска) и <em>STATUS</em> (при <em>попытках</em> &gt; 1 опрашивает, пока карта не объявит команду). У каждого действия есть проверка ответа: ожидаемые SW и данные (точно или маска с подстановкой <code class="font-mono text-sm">?</code> &mdash; <code class="font-mono text-sm">91??</code>) и проверка PoR для SCP80 (<em>любой / без PoR / por_ok</em>).</li>
<li><strong>Ожидания</strong> &mdash; карта должна объявить проактивную команду на предыдущем шаге (SW <code class="font-mono text-sm">91XX</code>, TS 102 221 &sect;7.4.2.1 / TS 102 223 &sect;6.3); <code class="font-mono text-sm">9000</code> означает &laquo;команды нет&raquo; и считается ошибкой &mdash; добавьте действие STATUS, если апплет выдаёт команду при опросе. Проверяются тип команды, квалификатор и содержимое (текст / пункт / raw), а <strong>TERMINAL RESPONSE</strong> (результат, идентификатор пункта, текст, доп. TLV) является частью инструкции.</li>
<li><strong>Уровни ошибок</strong> &mdash; несовпадение помечает шаг как <em>Ошибка</em> (скрипт останавливается) или <em>Предупреждение</em> (продолжает); каждая проверка показывается с ожидаемым и фактическим значением.</li>
<li><strong>Шаблоны</strong> &mdash; Empty, <em>Обзор меню STK</em>, <em>Апплет через SCP80</em>; редактор шагов — формный, отдельные скрипты экспортируются/импортируются как JSON.</li>
</ul>
<h2 id="server" class="text-xl font-semibold mb-3 border-b border-gray-300 dark:border-slate-700 pb-1">9. Установка сервера</h2>
<p class="mb-3">Для работы с картой (вкладка &laquo;Картридер&raquo;, &laquo;Симулятор телефона&raquo;, доставка OTA) нужен локальный <a href="https://github.com/anttro/simple" class="text-blue-600 dark:text-blue-400 hover:underline">pysim-simple-server</a> — встроенный в SIMple HTTP-сервер, оборачивающий pySim, работающий с ридером через PC/SC или serial и раздающий сам PWA (откройте <code class="font-mono text-sm">http://127.0.0.1:8080</code>).</p>