@naparnik/mcp 0.10.43 → 0.10.48

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/cli.js CHANGED
@@ -1,5 +1,5 @@
1
1
  #!/usr/bin/env node
2
- import { Engine, chooseBody, handOverToBody, VERSION, rollback, rollbackShell, remove, fromNpxCache, install, keyFromBlock, readConfig, ForeignBlockError, currentMachineFingerprint, CrashReporter, watchProcessCrashes, McpServer, buildAll, realPace, buildResources, StdioServerTransport, fromHost, WHERE_TO_GET_KEY, Wakefulness, systemBlocker, updateEngine, installStep, NaparnikApiClient, timeToCheck2, manifestUrlFor, fetchManifest, markChecked2, decide, shellDir, timeToCheck, bundleUrlFor, fetchShellManifest, markChecked, decideShell, installedShell, NaparnikConfigError } from './chunk-DQDZKXDU.js';
2
+ import { Engine, chooseBody, handOverToBody, VERSION, rollback, rollbackShell, remove, fromNpxCache, install, keyFromBlock, readConfig, ForeignBlockError, currentMachineFingerprint, CrashReporter, watchProcessCrashes, McpServer, buildAll, realPace, buildResources, StdioServerTransport, reportInstallFaults, fromHost, WHERE_TO_GET_KEY, Wakefulness, systemBlocker, updateEngine, installStep, NaparnikApiClient, timeToCheck2, manifestUrlFor, fetchManifest, markChecked2, decide, shellDir, timeToCheck, bundleUrlFor, fetchShellManifest, markChecked, decideShell, installedShell, NaparnikConfigError } from './chunk-Q7HJ7ROV.js';
3
3
  import { fileURLToPath } from 'url';
4
4
  import { realpathSync, readFileSync } from 'fs';
5
5
 
@@ -42,8 +42,8 @@ var HOW_MONTAGE_WORKS = `
42
42
  \u043C\u043E\u043B\u0447\u0430\u043D\u0438\u0435 \u0447\u0438\u0442\u0430\u0435\u0442\u0441\u044F \xAB\u0437\u0430\u0432\u0438\u0441\u043B\u043E\xBB. \u0413\u043E\u0442\u043E\u0432\u043E \u2014 preview.
43
43
  6. \u041F\u0440\u0430\u0432\u043A\u0430 \u0436\u0434\u0451\u0442 \u043F\u0435\u0447\u0430\u0442\u044C \u043F\u0440\u043E\u0447\u0438\u0442\u0430\u043D\u043D\u043E\u0439 \u0441\u0442\u0440\u0430\u043D\u0438\u0446\u044B (stamps, document/edits.md):
44
44
  \u0431\u0435\u0437 \u043D\u0435\u0451 plan_edit \u043E\u0442\u043A\u0430\u0436\u0435\u0442 \u0438 \u043F\u0440\u0438\u0448\u043B\u0451\u0442 \u0441\u0442\u0440\u0430\u043D\u0438\u0446\u0443.
45
- 7. \u0422\u044F\u0436\u0451\u043B\u043E\u0435 (\u0432\u044B\u0440\u0435\u0437 \u0433\u0435\u0440\u043E\u044F, \u0440\u0430\u0441\u043F\u043E\u0437\u043D\u0430\u0432\u0430\u043D\u0438\u0435 \u0440\u0435\u0447\u0438) \u2014 \u041F\u041E \u041F\u0420\u041E\u0421\u042C\u0411\u0415: \u043D\u0430\u0437\u043E\u0432\u0438 \u0432\u0435\u0441
46
- \u0438\u0437 setup, \u043F\u043E\u0441\u043B\u0435 \xAB\u0434\u0430\xBB setup \u0441 consent=true.
45
+ 7. \u0422\u044F\u0436\u0451\u043B\u043E\u0435 (\u0432\u044B\u0440\u0435\u0437 \u0433\u0435\u0440\u043E\u044F, \u0440\u0430\u0441\u043F\u043E\u0437\u043D\u0430\u0432\u0430\u043D\u0438\u0435 \u0440\u0435\u0447\u0438) \u2014 \u041F\u041E \u041F\u0420\u041E\u0421\u042C\u0411\u0415, \u0432\u0435\u0441 \u0438\u0437 setup.
46
+ \xAB\u0414\u0430\xBB, \xAB\u043E\u0431\u043D\u043E\u0432\u0438\xBB \u2014 \u041E\u0414\u0418\u041D setup \u0441 consent=true.
47
47
 
48
48
  \u0421\u043F\u0440\u0430\u0432\u043E\u0447\u043D\u0438\u043A \u0433\u043E\u0434\u0438\u0442\u0441\u044F \u0438 \u0431\u0435\u0437 \u0440\u043E\u043B\u0438\u043A\u0430: \u043F\u0440\u0435\u0437\u0435\u043D\u0442\u0430\u0446\u0438\u044F.
49
49
  \u041D\u0435 \u0432\u044B\u0434\u0443\u043C\u044B\u0432\u0430\u0439; \u0432\u0440\u0435\u043C\u044F \u2014 \u0442\u043E\u043B\u044C\u043A\u043E \u043E\u0442 \u0438\u043D\u0441\u0442\u0440\u0443\u043C\u0435\u043D\u0442\u0430.
@@ -436,11 +436,11 @@ async function start() {
436
436
  );
437
437
  }
438
438
  if (state.ok) {
439
- void awake.during(() => prepareEngine(engine, {
439
+ void awake.during(() => reportInstallFaults(crashes, () => prepareEngine(engine, {
440
440
  key: state.config.apiKey,
441
441
  baseUrl: state.config.baseUrl,
442
442
  tell: log
443
- })).catch((trouble) => {
443
+ }))).catch((trouble) => {
444
444
  log(`\u0434\u0432\u0438\u0436\u043E\u043A \u0434\u043E\u043A\u0430\u0447\u0430\u0442\u044C \u043D\u0435 \u0432\u044B\u0448\u043B\u043E: ${trouble instanceof Error ? trouble.message : String(trouble)}`);
445
445
  });
446
446
  }
package/dist/index.d.ts CHANGED
@@ -812,6 +812,34 @@ declare class Engine {
812
812
  enginePython(): string;
813
813
  /** Python подготовки кандидата — намеренно без fallback на venv старого пака. */
814
814
  bootstrapPython(): string;
815
+ /**
816
+ * Чем собирать окружение новой версии — по порядку, до первого, кто сумеет.
817
+ *
818
+ * ⚠ БАЗОВЫЙ ПИТОН РАБОЧЕЙ ВЕРСИИ СТОИТ ВПЕРЕДИ «python3» ИЗ PATH, И ЭТО
819
+ * ПОЧИНКА, А НЕ ВКУС. Claude Desktop на маке запускает нас без
820
+ * `/opt/homebrew/bin` в PATH, и «python3» там — `/usr/bin/python3`, питон
821
+ * Xcode 3.9. Он собирает venv только ссылками («This build of python cannot
822
+ * create venvs without using symlinks»), а ссылка на интерпретатор вне версии
823
+ * не проходит сверку `candidateVenvTrouble`. Обновление 2026.09.24-467 у
824
+ * владельца встало ровно на этом, хотя рабочая версия собрана Homebrew 3.14
825
+ * копиями и работает. Движок при первой установке ищет питон сам
826
+ * (`setup/python_finder.py`) и пишет, какой взял, в `pyvenv.cfg` окружения —
827
+ * этот и берём: он уже однажды собрал здесь рабочее окружение копиями.
828
+ *
829
+ * ⚠ НЕ ПИТОН САМОГО VENV. Окружение старой версии удаляется уборкой после
830
+ * обновления, и кандидат, собранный его питоном, остался бы без интерпретатора
831
+ * (`engine-candidate.test.ts`). База из `pyvenv.cfg` лежит вне версий.
832
+ */
833
+ bootstrapPythons(): string[];
834
+ /**
835
+ * Базовый интерпретатор окружения рабочей версии — из её `pyvenv.cfg`.
836
+ *
837
+ * `home` раньше `executable`: у Homebrew `executable` указывает в папку
838
+ * конкретного выпуска (`Cellar/python@3.14/3.14.7/…`), и после `brew upgrade`
839
+ * её уже нет, а `home` (`/opt/homebrew/opt/python@3.14/bin`) переживает
840
+ * обновление. Нет файла или записанного питона на диске — `null`.
841
+ */
842
+ workingBasePython(): string | null;
815
843
  /** Python ровно названного кандидата, а не текущей версии. */
816
844
  candidatePython(place: EnginePlace): string | null;
817
845
  /**
@@ -874,6 +902,19 @@ declare class Engine {
874
902
  stdout: string;
875
903
  stderr: string;
876
904
  }>;
905
+ /**
906
+ * То же, что `command`, но строки stderr уходят в `onLine` по мере печати.
907
+ *
908
+ * ⚠ РАДИ СКАЧИВАНИЯ НАЧИНКИ. `deliver` печатает «Скачано 3 МБ из 6 (50%)» в
909
+ * stderr по ходу, а `command` отдаёт всё разом в конце — и полоса обновления
910
+ * стояла без единой цифры, пока архив качался (владелец 2026-09-24: «как
911
+ * будто завис»). Строки те же, что у задач движка, и полоса разбирает их тем
912
+ * же `DOWNLOAD` (`job-report.ts`).
913
+ */
914
+ commandLive(args: string[], { timeout, key }: {
915
+ timeout?: number;
916
+ key?: string;
917
+ }, onLine: (line: string) => void): Promise<CommandOutcome>;
877
918
  /** Одна строка вывода команды — например, номер заведённого задания. */
878
919
  asString(place: EnginePlace, args: string[], key?: string): Promise<string>;
879
920
  /**
@@ -1155,6 +1196,12 @@ interface ScrubContext {
1155
1196
  secrets: string[];
1156
1197
  }
1157
1198
 
1199
+ /**
1200
+ * Что стало с отчётом — от этого зависят слова человеку.
1201
+ * `sent` — сервер принял (сейчас или раньше тот же отпечаток); `queued` —
1202
+ * лежит на диске и уйдёт с досылкой; `none` — не уйдёт (сервер отбил).
1203
+ */
1204
+ type Delivery = 'sent' | 'queued' | 'none';
1158
1205
  /** Хост — программа, в которой живёт оболочка (`clientInfo` рукопожатия MCP). */
1159
1206
  type Host = {
1160
1207
  name: string;
@@ -1210,8 +1257,17 @@ declare class CrashReporter {
1210
1257
  /** Запомнить строки аргументов вызова — чтобы вычеркнуть их из будущих отчётов. */
1211
1258
  noteSecrets(secrets: string[]): void;
1212
1259
  noteHost(host: Host | null): void;
1213
- /** Отправить отчёт мимо ответа. Для тестов и смоука — `settled()`. */
1214
- submit(crash: Crash): void;
1260
+ /**
1261
+ * Отправить отчёт. Ответ инструмента ждёт итог через {@link wordsFor}, а
1262
+ * всё прочее — нет; для тестов и смоука — `settled()`.
1263
+ */
1264
+ submit(crash: Crash): Promise<Delivery>;
1265
+ /**
1266
+ * Итог отправки для слов человеку — не дольше таймаута отправки с запасом.
1267
+ * Не успела — отчёт ещё в пути и либо уйдёт, либо ляжет в очередь: «уйдёт»
1268
+ * правда в обоих случаях.
1269
+ */
1270
+ outcome(delivery: Promise<Delivery>): Promise<Delivery>;
1215
1271
  /**
1216
1272
  * Процесс падает: отчёт кладётся на диск СИНХРОННО и уходит на следующем
1217
1273
  * запуске. Сеть здесь не трогаем — процессу осталось жить миллисекунды, и
@@ -1534,9 +1590,9 @@ declare class NaparnikConfigError extends NaparnikError {
1534
1590
  * годится ли она для новой начинки: разойдись она с пакетом, и в логах будет
1535
1591
  * стоять чужое число, а обновление начнёт считать оболочку не той.
1536
1592
  */
1537
- declare const VERSION = "0.10.43";
1593
+ declare const VERSION = "0.10.48";
1538
1594
  /** Как мы представляемся серверу Напарника. По нему в логах видно оболочку. */
1539
- declare const USER_AGENT = "naparnik-mcp/0.10.43";
1595
+ declare const USER_AGENT = "naparnik-mcp/0.10.48";
1540
1596
  /**
1541
1597
  * Самая старая начинка (движок монтажа), с которой эта оболочка работает.
1542
1598
  * Обновление начинки ниже этой версии не ставится, а выше — требует оболочки
@@ -1691,10 +1747,28 @@ interface UpdateDeps {
1691
1747
  timeout?: number;
1692
1748
  key?: string;
1693
1749
  }): Promise<CommandOutcome>;
1750
+ /** Команда со строками хода по мере печати; нет — скачивание идёт молча, как раньше. */
1751
+ commandLive?(args: string[], opts: {
1752
+ timeout?: number;
1753
+ key?: string;
1754
+ }, onLine: (line: string) => void): Promise<CommandOutcome>;
1694
1755
  enginePython(): string;
1695
1756
  pythonEnv(): NodeJS.ProcessEnv;
1696
1757
  }
1697
- interface DeployTestHooks {
1758
+ /**
1759
+ * Что обновлению сказать по ходу: строки скачивания и «скачал, дальше ставлю».
1760
+ *
1761
+ * ⚠ БЕЗ ЭТОГО ПОЛОСА СТОЯЛА НА «НАЧИНАЮ» ВЕСЬ ВЫЗОВ. Скачивание и сборка
1762
+ * окружения шли внутри одного `setup`, и человек 51 секунду не видел ни слова
1763
+ * (владелец 2026-09-24, Claude Desktop). Теперь обновление — задача
1764
+ * (`setup-job.ts`), и её этапы двигают ровно эти два крючка.
1765
+ */
1766
+ interface DeployHooks {
1767
+ /** Строка хода от движка: «Скачано 3 МБ из 6 (50%), осталось около 5 с». */
1768
+ line?(text: string): void;
1769
+ /** Архив скачан и разложен — дальше сборка окружения и проверка. */
1770
+ downloaded?(): void;
1771
+ /** Только для тестов: обрыв ровно между переименованием и записью кандидата. */
1698
1772
  afterPublishRename?(): void;
1699
1773
  }
1700
1774
  /**
@@ -1707,7 +1781,7 @@ interface DeployTestHooks {
1707
1781
  */
1708
1782
  declare function deploy(engine: UpdateDeps, manifest: EngineManifest, trial?: Trial,
1709
1783
  /** Ключ для закрытой раздачи движка: без него скачивание получит 403. */
1710
- key?: string, hooks?: DeployTestHooks): Promise<InstallOutcome>;
1784
+ key?: string, hooks?: DeployHooks): Promise<InstallOutcome>;
1711
1785
  /**
1712
1786
  * Дымовой прогон новой сборки: запускается ли она вообще и та ли это версия.
1713
1787
  * Возвращает текст беды или null, если всё в порядке.
package/dist/index.js CHANGED
@@ -1 +1 @@
1
- export { DEFAULT_HOME, DeliveryError, Engine, ForeignBlockError, INSIDE_PYTHON, INSTALL_STEPS, KEEP_COPIES, KEEP_VERSIONS, LONG_STEPS, MANIFEST_TIMEOUT_MS, MANIFEST_URL, MARKER, MIN_ENGINE, NaparnikApiClient, NaparnikAuthError, NaparnikClientError, NaparnikConfigError, NaparnikError, NaparnikInsufficientBalanceError, NaparnikScopeError, NaparnikServerError, NaparnikTimeoutError, PAUSE_HOURS, SERVER_NAME, SOURCES_FILE, START_SEC, TOOL_SEC, USER_AGENT, VERSION, buildAll, buildBlock, buildResources, compare, configPath, decide, defineTool, deploy, downloadFile, fetchManifest, fileOrRefusal, findBlock, fromNpxCache, inside, install, installPayload, installPython, jsonSchemaOf, keyInTable, lastLine, loadConfig, markChecked2 as markChecked, markCurrent, parseEngineManifest, parseFailure, path, platformKey, previousVersion, probe, pythonSource, refusalFor, remove, rollback, tarEntries, tidyOld, timeToCheck2 as timeToCheck, unpackArchive, withArgs } from './chunk-DQDZKXDU.js';
1
+ export { DEFAULT_HOME, DeliveryError, Engine, ForeignBlockError, INSIDE_PYTHON, INSTALL_STEPS, KEEP_COPIES, KEEP_VERSIONS, LONG_STEPS, MANIFEST_TIMEOUT_MS, MANIFEST_URL, MARKER, MIN_ENGINE, NaparnikApiClient, NaparnikAuthError, NaparnikClientError, NaparnikConfigError, NaparnikError, NaparnikInsufficientBalanceError, NaparnikScopeError, NaparnikServerError, NaparnikTimeoutError, PAUSE_HOURS, SERVER_NAME, SOURCES_FILE, START_SEC, TOOL_SEC, USER_AGENT, VERSION, buildAll, buildBlock, buildResources, compare, configPath, decide, defineTool, deploy, downloadFile, fetchManifest, fileOrRefusal, findBlock, fromNpxCache, inside, install, installPayload, installPython, jsonSchemaOf, keyInTable, lastLine, loadConfig, markChecked2 as markChecked, markCurrent, parseEngineManifest, parseFailure, path, platformKey, previousVersion, probe, pythonSource, refusalFor, remove, rollback, tarEntries, tidyOld, timeToCheck2 as timeToCheck, unpackArchive, withArgs } from './chunk-Q7HJ7ROV.js';
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@naparnik/mcp",
3
- "version": "0.10.43",
3
+ "version": "0.10.48",
4
4
  "description": "MCP-сервер Напарника: монтаж вертикального видео на машине пользователя — паузы, субтитры, герой на новом фоне, звук. Видео никуда не уезжает.",
5
5
  "license": "SEE LICENSE IN LICENSE.md",
6
6
  "private": false,