agent-bios 0.19.1 → 0.19.3

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.
Files changed (106) hide show
  1. package/DEPENDENCIES.md +58 -30
  2. package/INSTALL.md +4 -4
  3. package/README.md +105 -28
  4. package/claude/CLAUDE.md +1 -1
  5. package/claude/guides/claude-prompting.md +1 -1
  6. package/claude/guides/cli-multi-model-workflow.md +4 -4
  7. package/claude/guides/coding-staged-workflow.md +17 -0
  8. package/claude/guides/documentation-hygiene.md +3 -0
  9. package/claude/guides/gpt-prompting.md +1 -1
  10. package/claude/guides/korean-writing.md +153 -0
  11. package/claude/guides/learning-flow.md +4 -4
  12. package/claude/guides/llm-capability-boundary.md +7 -1
  13. package/claude/guides/session-distill-workflow.md +8 -8
  14. package/claude/guides/slide-writing/RUNBOOK.md +5 -5
  15. package/claude/guides/tooling-gotchas.md +20 -1
  16. package/claude/guides/ui-design/visual-direction.md +88 -0
  17. package/claude/guides/ui-design.md +90 -0
  18. package/claude/guides/verification-discipline.md +10 -1
  19. package/claude/hooks/tooling-gotchas-hook.py +41 -0
  20. package/claude/skills/repo-charter/SKILL.md +3 -3
  21. package/claude/skills/understand/SKILL.md +5 -5
  22. package/codex/AGENTS.md +1 -1
  23. package/codex/guides/claude-prompting.md +1 -1
  24. package/codex/guides/cli-multi-model-workflow.md +4 -4
  25. package/codex/guides/coding-staged-workflow.md +17 -0
  26. package/codex/guides/documentation-hygiene.md +3 -0
  27. package/codex/guides/gpt-prompting.md +1 -1
  28. package/codex/guides/korean-writing.md +153 -0
  29. package/codex/guides/learning-flow.md +4 -4
  30. package/codex/guides/llm-capability-boundary.md +7 -1
  31. package/codex/guides/session-distill-workflow.md +8 -8
  32. package/codex/guides/slide-writing/RUNBOOK.md +5 -5
  33. package/codex/guides/tooling-gotchas.md +20 -1
  34. package/codex/guides/ui-design/visual-direction.md +88 -0
  35. package/codex/guides/ui-design.md +90 -0
  36. package/codex/guides/verification-discipline.md +10 -1
  37. package/compose/app_bridge/SKILL.md +12 -12
  38. package/compose/app_bridge/scripts/bridge.py +35 -10
  39. package/compose/app_desktop/server.py +250 -0
  40. package/compose/assemble.py +5 -5
  41. package/compose/bootstrap/SKILL.md +18 -18
  42. package/compose/canary.sh +4 -4
  43. package/compose/check-domains.py +6 -6
  44. package/compose/corpus-state.py +16 -1168
  45. package/compose/corpus.py +13 -402
  46. package/compose/corpus_app.py +14 -450
  47. package/compose/corpus_catalog.py +15 -926
  48. package/compose/corpus_import.py +14 -523
  49. package/compose/corpus_install.py +14 -1847
  50. package/compose/corpus_session.py +16 -848
  51. package/compose/corpus_setup.py +16 -672
  52. package/compose/corpus_setup_cli.py +15 -580
  53. package/compose/corpus_setup_i18n.py +20 -324
  54. package/compose/corpus_setup_ui.py +18 -645
  55. package/compose/corpus_store.py +16 -1664
  56. package/compose/corpus_transaction.py +15 -284
  57. package/compose/corpus_ui.py +17 -972
  58. package/compose/corpus_ui_runtime.py +16 -274
  59. package/compose/corpus_understand.py +13 -671
  60. package/compose/domains.json +3 -1
  61. package/compose/host_platform.py +121 -0
  62. package/compose/instructions-state.py +1178 -0
  63. package/compose/instructions.py +409 -0
  64. package/compose/instructions_app.py +697 -0
  65. package/compose/instructions_catalog.py +931 -0
  66. package/compose/instructions_import.py +537 -0
  67. package/compose/instructions_install.py +1932 -0
  68. package/compose/instructions_session.py +852 -0
  69. package/compose/instructions_setup.py +713 -0
  70. package/compose/instructions_setup_cli.py +607 -0
  71. package/compose/instructions_setup_i18n.py +327 -0
  72. package/compose/instructions_setup_ui.py +647 -0
  73. package/compose/instructions_store.py +1668 -0
  74. package/compose/instructions_transaction.py +308 -0
  75. package/compose/instructions_ui.py +975 -0
  76. package/compose/instructions_ui_runtime.py +279 -0
  77. package/compose/instructions_understand.py +678 -0
  78. package/compose/native_cli.py +52 -0
  79. package/compose/register-hooks.py +1 -1
  80. package/compose/runtime_entry.py +58 -0
  81. package/compose/setup/START.md +11 -11
  82. package/compose/windows_deploy.py +719 -0
  83. package/docs/advanced-launch.md +11 -11
  84. package/docs/instructions-compatibility.md +86 -0
  85. package/docs/{corpus.md → instructions.md} +36 -8
  86. package/docs/recovery.md +10 -10
  87. package/docs/releases/0.19.2.md +38 -0
  88. package/docs/releases/0.19.3.md +107 -0
  89. package/docs/session-model.md +31 -20
  90. package/docs/setup.md +63 -26
  91. package/docs/understand.md +6 -6
  92. package/docs/windows.md +99 -0
  93. package/install.sh +71 -69
  94. package/launch/agent-launch.py +309 -293
  95. package/launch/agent-launch.toml +2 -2
  96. package/launch/agent-launch.zsh +11 -1
  97. package/launch/i18n/en.toml +55 -55
  98. package/launch/i18n/ja.toml +56 -56
  99. package/launch/i18n/ko.toml +56 -56
  100. package/launch/shell_integration.py +4 -4
  101. package/learn/collect-learning.py +10 -10
  102. package/learn/learning.schema.json +1 -1
  103. package/learn/migrate-learnings.py +51 -51
  104. package/package.json +33 -12
  105. package/provenance.json +1 -1
  106. /package/docs/assets/{corpus-studio.svg → instructions-studio.svg} +0 -0
@@ -107,7 +107,9 @@
107
107
  "svg-visualization-guide.md": {"tier": "domain", "domains": ["visualization-docs"], "item_id": "guide-svg-visualization-guide"},
108
108
  "slide-writing.md": {"tier": "domain", "domains": ["office-work", "visualization-docs"], "item_id": "skill-slide-writing"},
109
109
  "verification-discipline.md": {"tier": "domain", "domains": ["builder-base"], "item_id": "guide-verification-discipline"},
110
- "tooling-gotchas.md": {"tier": "domain", "domains": ["builder-base"], "item_id": "guide-tooling-gotchas"}
110
+ "tooling-gotchas.md": {"tier": "domain", "domains": ["builder-base"], "item_id": "guide-tooling-gotchas"},
111
+ "ui-design.md": {"tier": "domain", "domains": ["builder-base"], "item_id": "guide-ui-design"},
112
+ "korean-writing.md": {"tier": "core", "domains": [], "item_id": "korean-writing"}
111
113
  },
112
114
  "hooks": {
113
115
  "tooling-gotchas-hook.py": {"tier": "domain", "domains": ["builder-base"], "source_guide": "tooling-gotchas.md", "item_id": "hook-tooling-gotchas-hook"}
@@ -0,0 +1,121 @@
1
+ """Small OS boundary shared by the native entrypoint, installer and launcher."""
2
+ from __future__ import annotations
3
+ import errno
4
+ import os
5
+ from pathlib import Path
6
+ import subprocess
7
+ import sys
8
+ import time
9
+
10
+ WINDOWS = os.name == 'nt'
11
+
12
+ if not WINDOWS:
13
+ import fcntl as file_locks
14
+ else:
15
+ import msvcrt
16
+
17
+ class file_locks:
18
+ LOCK_EX, LOCK_NB, LOCK_UN = 2, 4, 8
19
+
20
+ @staticmethod
21
+ def flock(file, operation):
22
+ fd = file if isinstance(file, int) else file.fileno()
23
+ position = os.lseek(fd, 0, os.SEEK_CUR)
24
+ try:
25
+ while True:
26
+ os.lseek(fd, 0, os.SEEK_SET)
27
+ try:
28
+ msvcrt.locking(fd, msvcrt.LK_UNLCK if operation & 8 else msvcrt.LK_NBLCK, 1)
29
+ return
30
+ except OSError as exc:
31
+ if operation & 8 or exc.errno not in (errno.EACCES, errno.EAGAIN, errno.EDEADLK):
32
+ raise
33
+ if operation & 4:
34
+ raise BlockingIOError(exc.errno, str(exc)) from exc
35
+ time.sleep(.05)
36
+ finally:
37
+ os.lseek(fd, position, os.SEEK_SET)
38
+
39
+
40
+ def cli_argv(root: Path, *args: str) -> list[str]:
41
+ if WINDOWS:
42
+ return python_argv(root / 'compose/native_cli.py', *args)
43
+ return ['/bin/bash', str(root / 'install.sh'), *args]
44
+
45
+
46
+ def runtime_environment(environ=None) -> dict[str, str]:
47
+ env = os.environ if environ is None else environ
48
+ entry, deps = env.get('AGENT_BIOS_PYTHON_ENTRY'), env.get('AGENT_BIOS_PYTHON_DEPS')
49
+ if bool(entry) != bool(deps):
50
+ raise RuntimeError('application Python entry and dependencies must be bound together')
51
+ if not entry:
52
+ return {}
53
+ if not Path(entry).is_absolute() or not Path(entry).is_file() or not Path(deps).is_absolute() or not Path(deps).is_dir():
54
+ raise RuntimeError('application Python binding is unavailable; repair the script installation')
55
+ executable = env.get('AGENT_BIOS_PYTHON_EXECUTABLE', sys.executable)
56
+ if not Path(executable).is_absolute() or not Path(executable).is_file():
57
+ raise RuntimeError('bound Python interpreter is unavailable')
58
+ return {'AGENT_BIOS_PYTHON_ENTRY': str(entry), 'AGENT_BIOS_PYTHON_DEPS': str(deps), 'AGENT_BIOS_PYTHON_EXECUTABLE': str(executable)}
59
+
60
+
61
+ def python_argv(script: Path, *args: str, interpreter=None, environ=None) -> list[str]:
62
+ binding = runtime_environment(environ)
63
+ executable = str(interpreter or binding.get("AGENT_BIOS_PYTHON_EXECUTABLE") or sys.executable)
64
+ if binding:
65
+ return [executable, '-I', '-X', 'utf8', binding['AGENT_BIOS_PYTHON_ENTRY'],
66
+ '--dependencies', binding['AGENT_BIOS_PYTHON_DEPS'], '--script', str(script), *args]
67
+ return [executable, str(script), *args]
68
+
69
+
70
+ def sync_directory(path: Path) -> None:
71
+ # Windows CRT cannot open directory descriptors. File bytes are flushed by
72
+ # the writer; replace/restart tests establish process recovery, not power-loss durability.
73
+ if WINDOWS:
74
+ return
75
+ fd = os.open(path, os.O_RDONLY)
76
+ try:
77
+ os.fsync(fd)
78
+ finally:
79
+ os.close(fd)
80
+
81
+
82
+ def redirected(path: Path) -> bool:
83
+ return path.is_symlink() or (hasattr(path, 'is_junction') and path.is_junction())
84
+
85
+
86
+ def create_junction(link: Path, target: Path) -> None:
87
+ """Create a directory junction without shell expansion or symlink privileges."""
88
+ if not WINDOWS:
89
+ raise OSError('junction creation is Windows-only')
90
+ import ctypes
91
+ from ctypes import wintypes
92
+ import struct
93
+ kernel = ctypes.WinDLL('kernel32', use_last_error=True)
94
+ kernel.CreateFileW.argtypes = [wintypes.LPCWSTR, wintypes.DWORD, wintypes.DWORD, ctypes.c_void_p, wintypes.DWORD, wintypes.DWORD, wintypes.HANDLE]
95
+ kernel.CreateFileW.restype = wintypes.HANDLE
96
+ kernel.DeviceIoControl.argtypes = [wintypes.HANDLE, wintypes.DWORD, ctypes.c_void_p, wintypes.DWORD, ctypes.c_void_p, wintypes.DWORD, ctypes.POINTER(wintypes.DWORD), ctypes.c_void_p]
97
+ kernel.CloseHandle.argtypes = [wintypes.HANDLE]
98
+ target = target.resolve(strict=True)
99
+ substitute = ('\\??\\' + str(target)).encode('utf-16-le')
100
+ display = str(target).encode('utf-16-le')
101
+ names = substitute + b'\0\0' + display + b'\0\0'
102
+ payload = struct.pack('<HHHH', 0, len(substitute), len(substitute)+2, len(display)) + names
103
+ data = struct.pack('<IHH', 0xA0000003, len(payload), 0) + payload
104
+ link.mkdir()
105
+ handle = kernel.CreateFileW(str(link), 0x40000000, 0, None, 3, 0x02200000, None)
106
+ try:
107
+ if handle == ctypes.c_void_p(-1).value:
108
+ raise ctypes.WinError(ctypes.get_last_error())
109
+ returned = wintypes.DWORD()
110
+ buffer = ctypes.create_string_buffer(data)
111
+ if not kernel.DeviceIoControl(handle, 0x000900A4, buffer, len(data), None, 0, ctypes.byref(returned), None):
112
+ raise ctypes.WinError(ctypes.get_last_error())
113
+ except BaseException:
114
+ if handle != ctypes.c_void_p(-1).value:
115
+ kernel.CloseHandle(handle)
116
+ handle = ctypes.c_void_p(-1).value
117
+ link.rmdir()
118
+ raise
119
+ finally:
120
+ if handle != ctypes.c_void_p(-1).value:
121
+ kernel.CloseHandle(handle)