agentwire-dev 1.29.1__tar.gz → 1.29.2__tar.gz
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.
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/CHANGELOG.md +1 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/PKG-INFO +2 -1
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/__init__.py +1 -1
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/config.py +5 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/server.py +69 -21
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/css/desktop.css +273 -0
- agentwire_dev-1.29.2/agentwire/static/js/command-palette.js +601 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/desktop-manager.js +14 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/desktop.js +55 -7
- agentwire_dev-1.29.2/agentwire/static/js/pinned-message.js +232 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/sidebar/projects-section.js +3 -3
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/windows/chat-window.js +7 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/templates/desktop.html +1 -1
- agentwire_dev-1.29.2/docs/decisions/obsidian-second-brain.md +88 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/INDEX.md +3 -2
- agentwire_dev-1.29.2/docs/wiki/tts/stt-self-hosted.md +108 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/pyproject.toml +2 -0
- agentwire_dev-1.29.1/agentwire/static/js/quicktask-modal.js +0 -267
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/.github/FUNDING.yml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/.github/ISSUE_TEMPLATE/bug_report.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/.github/ISSUE_TEMPLATE/feature_request.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/.github/ISSUE_TEMPLATE/question.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/.github/PULL_REQUEST_TEMPLATE.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/.gitignore +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/CLA.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/CODE_OF_CONDUCT.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/CONTRIBUTING.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/Dockerfile.local +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/Dockerfile.runpod +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/LICENSE +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/README.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/RELEASING.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/SECURITY.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/SPONSORS.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/__main__.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/agents/__init__.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/agents/base.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/agents/tmux.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/cached_status.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/channels/__init__.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/channels/base.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/channels/email.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/channels/quo.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/cli_safety.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/completion.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/fetch.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/handoff/__init__.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/handoff/git_state.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/handoff/instructions.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/handoff/parser.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/handoff/renderer.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/handoff/schema.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/history.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/__init__.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/agentwire-permission.sh +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/damage-control/__init__.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/damage-control/audit_logger.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/damage-control/bash-tool-damage-control.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/damage-control/edit-tool-damage-control.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/damage-control/rules/agentwire.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/damage-control/rules/aws.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/damage-control/rules/cloud-hosting.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/damage-control/rules/containers.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/damage-control/rules/core.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/damage-control/rules/databases.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/damage-control/rules/firebase.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/damage-control/rules/gcp.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/damage-control/rules/git.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/damage-control/rules/gws.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/damage-control/rules/infrastructure.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/damage-control/rules/remote.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/damage-control/write-tool-damage-control.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/hooks/idle-handler.sh +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/listen.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/locking.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/mcp_server.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/missions/__init__.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/missions/cli.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/missions/config.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/missions/dispatcher.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/missions/eligibility.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/missions/feedback_router.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/missions/gc.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/missions/github.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/missions/naming.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/missions/state.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/network.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/onboarding.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/overnight.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/pane_manager.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/project_config.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/projects.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/prompts/__init__.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/prompts/init.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/roles/__init__.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/roles/agentwire.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/roles/chatbot.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/roles/init.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/roles/notifications.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/roles/orchestrator.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/roles/task-runner.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/roles/voice.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/roles/worker.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/safety/__init__.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/safety/_core.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/scheduler.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/search.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/agentwire-Echo--black.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/agentwire-Echo--transparent.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/agentwire-Echo.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/agentwire-email-banner.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/agentwire-splash-logo-layers--agentwire-text.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/agentwire-splash-logo-layers--echo-claw-fg.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/agentwire-splash-logo-layers--echo.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/agentwire-splash-logo-layers--full--transparent-top.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/agentwire-splash-logo-layers--full-black.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/agentwire-splash-logo-layers--telephone-fg.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/agentwire-splash-logo-layers--telephone.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/agentwire-splash-logo-layers--transparent-top.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/agentwire-splash-logo-layers--transparent.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/agentwire-splash-logo-layers--tree.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/agentwire-splash-logo-layers.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/favicon.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/machines/android.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/machines/automaton.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/machines/bot.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/machines/cyborg.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/machines/droid.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/machines/drone.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/machines/guardian.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/machines/mech.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/machines/probe.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/machines/robot.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/machines/sentinel.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/machines/unit.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/projects/blob.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/projects/cloud.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/projects/crystal.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/projects/cyclops.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/projects/flame.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/projects/fuzzy.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/projects/horned.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/projects/moon.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/projects/slime.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/projects/star.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/projects/tentacle.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/projects/winged.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/sessions/bear.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/sessions/cat.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/sessions/crown.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/sessions/custom/agentwire-portal.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/sessions/custom/agentwire-tts.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/sessions/custom/agentwire.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/sessions/deer.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/sessions/drone.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/sessions/eagle.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/sessions/fox.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/sessions/hawk.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/sessions/horse.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/sessions/lion.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/sessions/rabbit.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/sessions/robot.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/sessions/tiger.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/icons/sessions/wolf.jpeg +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/.gitkeep +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/artifact-window.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/components/icon-picker.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/components/list-card.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/components/type-tag.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/icon-manager.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/new-project-modal.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/notifications-panel.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/safety-shared.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/safety-window.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/session-id.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/session-window.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/sidebar/artifacts-section.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/sidebar/config-section.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/sidebar/machines-section.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/sidebar/missions-section.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/sidebar/safety-section.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/sidebar/scheduler-section.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/sidebar/services-section.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/sidebar/sessions-section.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/sidebar.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/terminal-font-prefs.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/tile-manager.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/utils/auto-refresh.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/static/js/winbox.bundle.min.js +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/stt/__init__.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/stt/base.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/stt/server_backend.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/stt/stt_server.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/stt/whisperkit.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tasks.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/templates/__init__.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/templates/base.html +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/templates/email_notification.html +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/templates/handoff/show-the-story.html.j2 +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/templates/handoff/theme.css.j2 +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/templates/tmux.conf +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/templating.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tooldefs/aws.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tooldefs/docker.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tooldefs/gcp.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tooldefs/gh.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tooldefs/git.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tooldefs/gws.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tooldefs/kubectl.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tooldefs/npm.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tooldefs/terraform.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tooldefs/uv.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tts/__init__.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tts/base.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tts/engines/__init__.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tts/engines/chatterbox.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tts/engines/kokoro.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tts/engines/qwen_base.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tts/engines/qwen_custom.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tts/engines/qwen_design.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tts/engines/zonos.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tts/registry.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tts/runpod_handler.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tts_server.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/tunnels.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/utils/__init__.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/utils/chunker.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/utils/file_io.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/utils/paths.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/utils/subprocess.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/validation.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/voiceclone.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/voices/darren.wav +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/voices/default.wav +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/voices/jessica.wav +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/voices/lisa.wav +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/voices/may.wav +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/agentwire/worktree.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/logo.png +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/architecture.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/communication/channels.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/communication/hammerspoon.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/communication/handoff.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/concepts.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/deployment/remote-access.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/deployment/remote-machines.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/glossary.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/integrations/gws-google-workspace-cli.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/internals/damage-control.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/internals/portal.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/internals/shell-escaping.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/internals/troubleshooting.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/missions.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/quickstart.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/scheduling/scheduled-workloads.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/sessions/claude-code-auto-mode.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/sessions/pi.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/tts/runpod-tts.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/docs/wiki/tts/tts-self-hosted.md +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/requirements-tts.txt +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/templates/launchd/dev.agentwire.mission-dispatcher.plist +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/templates/launchd/dev.agentwire.mission-feedback-router.plist +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/templates/launchd/dev.agentwire.mission-janitor.plist +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/conftest.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/e2e/test_portal_ui.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/fixtures/sample_agentwire.yml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/fixtures/sample_config.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/fixtures/sample_scheduler.yaml +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/integration/test_missions_concurrency.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/integration/test_missions_lifecycle.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/integration/test_scheduler_board.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/integration/test_server_websockets.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_build_agent_command.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_channels.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_cli_commands.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_cli_output.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_cli_safety.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_config.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_damage_control_hooks.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_damage_control_sync.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_file_io.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_handoff_git_state.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_handoff_instructions.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_handoff_parser.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_handoff_renderer.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_history.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_locking.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_mcp_server.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_mcp_tools_args.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_missions_cli.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_missions_config.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_missions_dispatcher.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_missions_eligibility.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_missions_feedback_router.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_missions_gc.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_missions_github.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_missions_naming.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_missions_state.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_overnight_resume_flags.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_portal_api.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_project_config.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_roles.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_safety_disabled_rules.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_safety_escape_hatch.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_safety_kill_switch.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_safety_mission_worker.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_scheduler.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_scheduler_parsing.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_search.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_server_async.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_server_pure.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_tasks.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_templating.py +0 -0
- {agentwire_dev-1.29.1 → agentwire_dev-1.29.2}/tests/unit/test_worktree.py +0 -0
|
@@ -10,6 +10,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
|
|
10
10
|
### Removed
|
|
11
11
|
|
|
12
12
|
- **Workflow engine** — entire `agentwire/workflows/` package (DAG runner, definitions, storage, pi runner, CLI), the `agentwire workflow` CLI subcommand, 5 MCP tools (`workflow_list/validate/run/history/show`), 3 portal endpoints (`/api/workflows/list|runs|runs/{id}`), the Workflows sidebar section + WorkflowWindow + ~230 lines of CSS, the scheduler's `workflow:` dispatch branch (`SchedulerTask.workflow`/`inputs` fields, `_dispatch_workflow_task`, `_render_workflow_inputs`, `_parse_workflow_summary`, `_workflow_failure_state`, validation block), 9 workflow test files plus the workflow-specific cases in `test_scheduler.py`, the `agentwire-workflows` skill, `docs/wiki/scheduling/workflows.md`, and ~120 dirs of historical runs under `~/.agentwire/workflows/`. The user's actual recurring automations all live as scheduler ensure tasks (`task:`); the engine was unused in practice and the empty sidebar surface was just noise. Scheduler is now ensure-only.
|
|
13
|
+
- **On-hold mission docs** — retroactive accounting for the seven on-hold files left behind by #153 and wholesale-deleted in commit `2425847` (2026-05-13) as part of the GitHub-issues-as-SSOT migration: `docs/missions/OBJECTIVE.md` (folded into README + website), `docs/missions/pi-harness-overview.md` (roadmap superseded — phases shipped or moved to research wiki), `docs/missions/pi-workflow-advanced.md` (on-hold-awaiting-usage stance has no scoped plan to track), `docs/missions/pi-workflow-ui.md` (visible portion shipped; speculative remainder unscoped), `docs/missions/later/multi-channel-bus.md` (premise actively rejected — wire surface is now outbound-only), `docs/missions/later/personal-replica.md` (speculative ideation, not a plan), `docs/missions/later/ralph-loop-use-cases.md` (brainstorm artifact). Closes [#154](https://github.com/dotdevdotdev/agentwire-dev/issues/154).
|
|
13
14
|
- **Inbound channel surface** — entire Telegram bridge (`agentwire/bridges/telegram.py`), Discord channel (`agentwire/channels/discord.py`), Slack channel (`agentwire/channels/slack.py`), Twilio SMS (`agentwire/channels/sms.py`), Webhook (`agentwire/channels/webhook.py`), outbound-Telegram (`agentwire/channels/telegram.py`), channel scaffolding template (`agentwire/channels/_template.py`), all `agentwire {telegram,discord,slack,sms,webhook}` CLI command groups, the `agentwire reply` command, MCP tools `discord_status` / `slack_status` / `sms_send` / `webhook_send`, the portal sidebar "socials" section, the `ServiceChannel` / `MessageQueueManager` / `QueuedMessage` / `compose_session_config` / `inject_instructions` / session-helper plumbing in `channels/base.py`, the TTS/STT primitives on the channel base class, the auto-injected `discord-dm` / `slack-dm` / `channel-admin` roles, the `OutputConfig.notify` task field plus its `_handle_task_notification` dispatcher (voice / alert / webhook / email / command), the doctor's Telegram bridge check, and the `aiogram` optional dep. Wire surface is now outbound-only: **email** (Resend) and **quo** (OpenPhone SMS) remain. Inbound user input flows through the portal. Security review traced the cut: Telegram bridge was secure (refuse-to-start on empty allowlist + silent default-deny), Discord/Slack fail-open on empty allowlist + unauthenticated channel `@mention`; rather than fix the gaps, the whole inbound surface comes out to keep the wire posture outbound-only.
|
|
14
15
|
- **Anthropic SDK surface** — entire `agentwire/sdk/` package, `agentwire/repl/` (Textual REPL), `agentwire/workflows/runners/{anthropic,human_gate}.py`, `sdk-bypass` / `sdk-prompted` / `sdk-restricted` session types, `sdk-watch` portal window + sidebar section, `--runner` workflow CLI override, and the `claude-agent-sdk` dependency. Anthropic moved Agent SDK + `claude -p` usage out of the monthly subscription tier on 2026-05-13 (now API-billed); the in-tree consumers were too expensive to keep running. The `pi` workflow runner is now the only runner. For Anthropic-quality scheduled work, use a `claude-bypass` tmux session via `.agentwire.yml` + scheduler. Mission [#184](https://github.com/dotdevdotdev/agentwire-dev/issues/184). Findings captured in `~/.agentwire/wiki/` (anthropic-agent-sdk, anthropic-runner-findings, textual-repl-retrospective, workflow-runner-choice, claude-code-print-mode).
|
|
15
16
|
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: agentwire-dev
|
|
3
|
-
Version: 1.29.
|
|
3
|
+
Version: 1.29.2
|
|
4
4
|
Summary: Multi-session voice web interface for AI coding agents
|
|
5
5
|
Project-URL: Homepage, https://agentwire.dev
|
|
6
6
|
Project-URL: Repository, https://github.com/dotdevdotdev/agentwire-dev
|
|
@@ -686,6 +686,7 @@ Classifier: Topic :: Software Development :: User Interfaces
|
|
|
686
686
|
Requires-Python: >=3.10
|
|
687
687
|
Requires-Dist: aiohttp-jinja2>=1.6
|
|
688
688
|
Requires-Dist: aiohttp>=3.9.0
|
|
689
|
+
Requires-Dist: av>=12.0.0
|
|
689
690
|
Requires-Dist: jinja2>=3.1.0
|
|
690
691
|
Requires-Dist: markdown>=3.5
|
|
691
692
|
Requires-Dist: mcp>=1.2.0
|
|
@@ -109,6 +109,10 @@ class STTConfig:
|
|
|
109
109
|
|
|
110
110
|
url: str | None = None # STT server URL (e.g., http://localhost:8100)
|
|
111
111
|
timeout: int = 30
|
|
112
|
+
# Milliseconds of silence to prepend to the decoded audio before sending
|
|
113
|
+
# to the STT backend. Default 0 — moonshine doesn't need it. Set to ~300
|
|
114
|
+
# if your backend (e.g. older faster-whisper builds) clips the first syllable.
|
|
115
|
+
silence_prepend_ms: int = 0
|
|
112
116
|
|
|
113
117
|
|
|
114
118
|
@dataclass
|
|
@@ -406,6 +410,7 @@ def _dict_to_config(data: dict) -> Config:
|
|
|
406
410
|
stt = STTConfig(
|
|
407
411
|
url=stt_data.get("url"),
|
|
408
412
|
timeout=stt_data.get("timeout", 30),
|
|
413
|
+
silence_prepend_ms=int(stt_data.get("silence_prepend_ms", 0)),
|
|
409
414
|
)
|
|
410
415
|
|
|
411
416
|
# Agent
|
|
@@ -3283,7 +3283,13 @@ projects:
|
|
|
3283
3283
|
return web.json_response({"error": str(e)}, status=500)
|
|
3284
3284
|
|
|
3285
3285
|
async def handle_transcribe(self, request: web.Request) -> web.Response:
|
|
3286
|
-
"""Transcribe audio to text.
|
|
3286
|
+
"""Transcribe audio to text.
|
|
3287
|
+
|
|
3288
|
+
Decodes WebM/Opus uploads in-process via PyAV (no ffmpeg subprocess
|
|
3289
|
+
startup) and resamples to 16 kHz mono PCM16 — the canonical input
|
|
3290
|
+
shape for Whisper- and Moonshine-class models. Optionally prepends a
|
|
3291
|
+
configurable amount of silence (``stt.silence_prepend_ms``, default 0).
|
|
3292
|
+
"""
|
|
3287
3293
|
try:
|
|
3288
3294
|
reader = await request.multipart()
|
|
3289
3295
|
audio_field = await reader.next()
|
|
@@ -3291,46 +3297,88 @@ projects:
|
|
|
3291
3297
|
if audio_field is None:
|
|
3292
3298
|
return web.json_response({"error": "No audio data"})
|
|
3293
3299
|
|
|
3294
|
-
# Read audio data
|
|
3295
3300
|
audio_data = await audio_field.read()
|
|
3296
|
-
|
|
3297
3301
|
if not audio_data:
|
|
3298
3302
|
return web.json_response({"error": "Empty audio data"})
|
|
3299
3303
|
|
|
3300
|
-
|
|
3301
|
-
with tempfile.NamedTemporaryFile(suffix=".webm", delete=False) as f:
|
|
3302
|
-
f.write(audio_data)
|
|
3303
|
-
webm_path = f.name
|
|
3304
|
+
silence_ms = int(getattr(self.config.stt, "silence_prepend_ms", 0) or 0)
|
|
3304
3305
|
|
|
3305
|
-
# Convert webm to wav (16kHz mono for Whisper)
|
|
3306
|
-
wav_path = webm_path.replace(".webm", ".wav")
|
|
3307
3306
|
try:
|
|
3308
|
-
|
|
3309
|
-
|
|
3310
|
-
|
|
3311
|
-
|
|
3312
|
-
|
|
3313
|
-
stderr=asyncio.subprocess.DEVNULL,
|
|
3307
|
+
wav_data = await asyncio.get_event_loop().run_in_executor(
|
|
3308
|
+
None,
|
|
3309
|
+
self._decode_audio_to_wav,
|
|
3310
|
+
audio_data,
|
|
3311
|
+
silence_ms,
|
|
3314
3312
|
)
|
|
3315
|
-
|
|
3313
|
+
except Exception as e:
|
|
3314
|
+
logger.error("Failed to decode audio: %s", e)
|
|
3315
|
+
return web.json_response({"error": "Audio conversion failed"})
|
|
3316
3316
|
|
|
3317
|
-
|
|
3318
|
-
|
|
3319
|
-
|
|
3317
|
+
with tempfile.NamedTemporaryFile(suffix=".wav", delete=False) as f:
|
|
3318
|
+
f.write(wav_data)
|
|
3319
|
+
wav_path = f.name
|
|
3320
3320
|
|
|
3321
|
-
|
|
3321
|
+
try:
|
|
3322
3322
|
logger.info("Transcribing %s via %s backend", wav_path, type(self.stt).__name__)
|
|
3323
3323
|
text = await self.stt.transcribe(Path(wav_path))
|
|
3324
3324
|
logger.info("Transcription result: %s", text)
|
|
3325
3325
|
return web.json_response({"text": text})
|
|
3326
3326
|
finally:
|
|
3327
|
-
Path(webm_path).unlink(missing_ok=True)
|
|
3328
3327
|
Path(wav_path).unlink(missing_ok=True)
|
|
3329
3328
|
|
|
3330
3329
|
except Exception as e:
|
|
3331
3330
|
logger.error(f"Transcription failed: {e}")
|
|
3332
3331
|
return web.json_response({"error": str(e)})
|
|
3333
3332
|
|
|
3333
|
+
@staticmethod
|
|
3334
|
+
def _decode_audio_to_wav(audio_data: bytes, silence_prepend_ms: int = 0) -> bytes:
|
|
3335
|
+
"""Decode arbitrary input audio (WebM/Opus, MP3, M4A, …) to 16 kHz mono PCM16 WAV.
|
|
3336
|
+
|
|
3337
|
+
Replaces the previous ``ffmpeg -i in.webm out.wav`` subprocess. Subprocess
|
|
3338
|
+
cold-start was 100–300 ms before any actual decoding; PyAV uses libav
|
|
3339
|
+
bindings in-process so the only cost is the decoding itself.
|
|
3340
|
+
"""
|
|
3341
|
+
import io
|
|
3342
|
+
import wave
|
|
3343
|
+
|
|
3344
|
+
import av # PyAV — declared in pyproject.toml `dependencies`
|
|
3345
|
+
|
|
3346
|
+
target_rate = 16000
|
|
3347
|
+
|
|
3348
|
+
with av.open(io.BytesIO(audio_data), mode="r") as container:
|
|
3349
|
+
if not container.streams.audio:
|
|
3350
|
+
raise RuntimeError("Input contains no audio stream")
|
|
3351
|
+
|
|
3352
|
+
resampler = av.AudioResampler(format="s16", layout="mono", rate=target_rate)
|
|
3353
|
+
pcm_chunks: list[bytes] = []
|
|
3354
|
+
|
|
3355
|
+
def _frame_bytes(f) -> bytes:
|
|
3356
|
+
# AudioFrame.planes[0] may include SIMD alignment padding; slice
|
|
3357
|
+
# to the exact PCM length (samples × channels × bytes_per_sample).
|
|
3358
|
+
bytes_per_sample = f.format.bytes # 2 for s16
|
|
3359
|
+
channels = len(f.layout.channels) # 1 for mono
|
|
3360
|
+
size = f.samples * channels * bytes_per_sample
|
|
3361
|
+
return bytes(f.planes[0])[:size]
|
|
3362
|
+
|
|
3363
|
+
for frame in container.decode(audio=0):
|
|
3364
|
+
for resampled in resampler.resample(frame):
|
|
3365
|
+
pcm_chunks.append(_frame_bytes(resampled))
|
|
3366
|
+
for resampled in resampler.resample(None):
|
|
3367
|
+
pcm_chunks.append(_frame_bytes(resampled))
|
|
3368
|
+
|
|
3369
|
+
if silence_prepend_ms > 0:
|
|
3370
|
+
silence_samples = int(target_rate * silence_prepend_ms / 1000)
|
|
3371
|
+
pcm_chunks.insert(0, b"\x00\x00" * silence_samples)
|
|
3372
|
+
|
|
3373
|
+
pcm_data = b"".join(pcm_chunks)
|
|
3374
|
+
buf = io.BytesIO()
|
|
3375
|
+
with wave.open(buf, "wb") as wav:
|
|
3376
|
+
wav.setnchannels(1)
|
|
3377
|
+
wav.setsampwidth(2) # 16-bit
|
|
3378
|
+
wav.setframerate(target_rate)
|
|
3379
|
+
wav.writeframes(pcm_data)
|
|
3380
|
+
return buf.getvalue()
|
|
3381
|
+
|
|
3334
3382
|
async def handle_upload(self, request: web.Request) -> web.Response:
|
|
3335
3383
|
"""Upload an image file for attachment to messages."""
|
|
3336
3384
|
try:
|
|
@@ -1162,6 +1162,111 @@ body {
|
|
|
1162
1162
|
text-align: center;
|
|
1163
1163
|
}
|
|
1164
1164
|
|
|
1165
|
+
/* =========================================================================
|
|
1166
|
+
Command palette (Cmd/Ctrl+K)
|
|
1167
|
+
========================================================================= */
|
|
1168
|
+
|
|
1169
|
+
.cmdk-overlay {
|
|
1170
|
+
align-items: flex-start;
|
|
1171
|
+
padding-top: 12vh;
|
|
1172
|
+
}
|
|
1173
|
+
|
|
1174
|
+
.command-palette {
|
|
1175
|
+
width: 560px;
|
|
1176
|
+
max-width: 92vw;
|
|
1177
|
+
display: flex;
|
|
1178
|
+
flex-direction: column;
|
|
1179
|
+
overflow: hidden;
|
|
1180
|
+
}
|
|
1181
|
+
|
|
1182
|
+
.cmdk-search {
|
|
1183
|
+
display: flex;
|
|
1184
|
+
align-items: center;
|
|
1185
|
+
gap: 10px;
|
|
1186
|
+
padding: 12px 16px;
|
|
1187
|
+
border-bottom: 1px solid var(--chrome-border);
|
|
1188
|
+
}
|
|
1189
|
+
|
|
1190
|
+
.cmdk-search-icon {
|
|
1191
|
+
color: var(--text-muted);
|
|
1192
|
+
font-size: 16px;
|
|
1193
|
+
}
|
|
1194
|
+
|
|
1195
|
+
.cmdk-input {
|
|
1196
|
+
flex: 1;
|
|
1197
|
+
background: transparent;
|
|
1198
|
+
border: none;
|
|
1199
|
+
outline: none;
|
|
1200
|
+
color: var(--text);
|
|
1201
|
+
font-size: 16px;
|
|
1202
|
+
font-family: inherit;
|
|
1203
|
+
}
|
|
1204
|
+
|
|
1205
|
+
.cmdk-input::placeholder {
|
|
1206
|
+
color: var(--text-muted);
|
|
1207
|
+
}
|
|
1208
|
+
|
|
1209
|
+
.cmdk-body {
|
|
1210
|
+
padding: 8px;
|
|
1211
|
+
max-height: 50vh;
|
|
1212
|
+
overflow-y: auto;
|
|
1213
|
+
}
|
|
1214
|
+
|
|
1215
|
+
/* Form drill-ins reuse the quicktask form styling. */
|
|
1216
|
+
.cmdk-body .quicktask-form {
|
|
1217
|
+
padding: 8px 8px 4px;
|
|
1218
|
+
}
|
|
1219
|
+
|
|
1220
|
+
.cmdk-item {
|
|
1221
|
+
display: flex;
|
|
1222
|
+
align-items: center;
|
|
1223
|
+
gap: 12px;
|
|
1224
|
+
padding: 10px 12px;
|
|
1225
|
+
border-radius: 6px;
|
|
1226
|
+
cursor: pointer;
|
|
1227
|
+
font-size: 14px;
|
|
1228
|
+
color: var(--text);
|
|
1229
|
+
}
|
|
1230
|
+
|
|
1231
|
+
.cmdk-item-selected {
|
|
1232
|
+
background: var(--accent);
|
|
1233
|
+
color: var(--background);
|
|
1234
|
+
}
|
|
1235
|
+
|
|
1236
|
+
.cmdk-item-icon {
|
|
1237
|
+
width: 18px;
|
|
1238
|
+
text-align: center;
|
|
1239
|
+
opacity: 0.85;
|
|
1240
|
+
}
|
|
1241
|
+
|
|
1242
|
+
.cmdk-item-label {
|
|
1243
|
+
flex: 1;
|
|
1244
|
+
}
|
|
1245
|
+
|
|
1246
|
+
.cmdk-item-sub {
|
|
1247
|
+
font-size: 12px;
|
|
1248
|
+
color: var(--text-muted);
|
|
1249
|
+
}
|
|
1250
|
+
|
|
1251
|
+
.cmdk-item-selected .cmdk-item-sub {
|
|
1252
|
+
color: var(--background);
|
|
1253
|
+
opacity: 0.8;
|
|
1254
|
+
}
|
|
1255
|
+
|
|
1256
|
+
.cmdk-empty {
|
|
1257
|
+
padding: 20px 12px;
|
|
1258
|
+
text-align: center;
|
|
1259
|
+
color: var(--text-muted);
|
|
1260
|
+
font-size: 14px;
|
|
1261
|
+
}
|
|
1262
|
+
|
|
1263
|
+
.cmdk-footer {
|
|
1264
|
+
padding: 8px 16px;
|
|
1265
|
+
border-top: 1px solid var(--chrome-border);
|
|
1266
|
+
font-size: 12px;
|
|
1267
|
+
color: var(--text-muted);
|
|
1268
|
+
}
|
|
1269
|
+
|
|
1165
1270
|
.sidebar-quicktask {
|
|
1166
1271
|
background: transparent;
|
|
1167
1272
|
border: none;
|
|
@@ -4601,3 +4706,171 @@ body.sidebar-pinned .sidebar-tab {
|
|
|
4601
4706
|
}
|
|
4602
4707
|
|
|
4603
4708
|
|
|
4709
|
+
/* =========================================================================
|
|
4710
|
+
Pinned Message Panel — floating, draggable, resizable
|
|
4711
|
+
========================================================================= */
|
|
4712
|
+
|
|
4713
|
+
/* Pin affordance on chat messages — visible on hover, top-right corner. */
|
|
4714
|
+
.chat-message {
|
|
4715
|
+
position: relative;
|
|
4716
|
+
padding-right: 32px;
|
|
4717
|
+
}
|
|
4718
|
+
|
|
4719
|
+
.chat-message-pin-btn {
|
|
4720
|
+
position: absolute;
|
|
4721
|
+
top: 4px;
|
|
4722
|
+
right: 4px;
|
|
4723
|
+
width: 22px;
|
|
4724
|
+
height: 22px;
|
|
4725
|
+
padding: 0;
|
|
4726
|
+
border: 1px solid var(--chrome-border);
|
|
4727
|
+
border-radius: 4px;
|
|
4728
|
+
background: var(--chrome);
|
|
4729
|
+
color: var(--text-muted);
|
|
4730
|
+
font-size: 12px;
|
|
4731
|
+
line-height: 1;
|
|
4732
|
+
cursor: pointer;
|
|
4733
|
+
opacity: 0;
|
|
4734
|
+
transition: opacity 120ms ease, color 120ms ease, background 120ms ease;
|
|
4735
|
+
}
|
|
4736
|
+
|
|
4737
|
+
.chat-message:hover .chat-message-pin-btn,
|
|
4738
|
+
.chat-message:focus-within .chat-message-pin-btn,
|
|
4739
|
+
.chat-message-pin-btn:focus-visible {
|
|
4740
|
+
opacity: 0.9;
|
|
4741
|
+
}
|
|
4742
|
+
|
|
4743
|
+
.chat-message-pin-btn:hover {
|
|
4744
|
+
background: var(--hover);
|
|
4745
|
+
color: var(--accent);
|
|
4746
|
+
opacity: 1;
|
|
4747
|
+
}
|
|
4748
|
+
|
|
4749
|
+
.chat-message-pin-btn[data-pinned="true"] {
|
|
4750
|
+
opacity: 1;
|
|
4751
|
+
color: var(--accent);
|
|
4752
|
+
border-color: var(--accent);
|
|
4753
|
+
}
|
|
4754
|
+
|
|
4755
|
+
/* The floating panel itself. position: fixed keeps it above all winboxes
|
|
4756
|
+
regardless of scroll, typing, or which session window is active. */
|
|
4757
|
+
.pinned-message-panel {
|
|
4758
|
+
position: fixed;
|
|
4759
|
+
display: flex;
|
|
4760
|
+
flex-direction: column;
|
|
4761
|
+
background: var(--chrome);
|
|
4762
|
+
color: var(--text);
|
|
4763
|
+
border: 1px solid var(--chrome-border);
|
|
4764
|
+
border-radius: 8px;
|
|
4765
|
+
box-shadow: 0 10px 30px rgba(0, 0, 0, 0.55), 0 0 0 1px var(--primary-subtle);
|
|
4766
|
+
z-index: 99998;
|
|
4767
|
+
min-width: 200px;
|
|
4768
|
+
min-height: 140px;
|
|
4769
|
+
overflow: hidden;
|
|
4770
|
+
user-select: text;
|
|
4771
|
+
}
|
|
4772
|
+
|
|
4773
|
+
.pinned-message-panel.dragging,
|
|
4774
|
+
.pinned-message-panel.resizing {
|
|
4775
|
+
user-select: none;
|
|
4776
|
+
}
|
|
4777
|
+
|
|
4778
|
+
.pinned-message-header {
|
|
4779
|
+
display: flex;
|
|
4780
|
+
align-items: center;
|
|
4781
|
+
gap: 8px;
|
|
4782
|
+
padding: 6px 10px;
|
|
4783
|
+
background: var(--background);
|
|
4784
|
+
border-bottom: 1px solid var(--chrome-border);
|
|
4785
|
+
cursor: grab;
|
|
4786
|
+
flex-shrink: 0;
|
|
4787
|
+
}
|
|
4788
|
+
|
|
4789
|
+
.pinned-message-panel.dragging .pinned-message-header {
|
|
4790
|
+
cursor: grabbing;
|
|
4791
|
+
}
|
|
4792
|
+
|
|
4793
|
+
.pinned-message-role {
|
|
4794
|
+
font-size: 11px;
|
|
4795
|
+
text-transform: uppercase;
|
|
4796
|
+
letter-spacing: 0.06em;
|
|
4797
|
+
padding: 2px 6px;
|
|
4798
|
+
border-radius: 4px;
|
|
4799
|
+
background: var(--chrome);
|
|
4800
|
+
color: var(--text-muted);
|
|
4801
|
+
border: 1px solid var(--chrome-border);
|
|
4802
|
+
flex-shrink: 0;
|
|
4803
|
+
}
|
|
4804
|
+
|
|
4805
|
+
.pinned-message-role[data-role="user"] {
|
|
4806
|
+
color: var(--accent);
|
|
4807
|
+
border-color: var(--primary-subtle);
|
|
4808
|
+
}
|
|
4809
|
+
|
|
4810
|
+
.pinned-message-title {
|
|
4811
|
+
flex: 1;
|
|
4812
|
+
font-size: 12px;
|
|
4813
|
+
color: var(--text-muted);
|
|
4814
|
+
text-transform: uppercase;
|
|
4815
|
+
letter-spacing: 0.08em;
|
|
4816
|
+
overflow: hidden;
|
|
4817
|
+
white-space: nowrap;
|
|
4818
|
+
text-overflow: ellipsis;
|
|
4819
|
+
}
|
|
4820
|
+
|
|
4821
|
+
.pinned-message-unpin {
|
|
4822
|
+
width: 22px;
|
|
4823
|
+
height: 22px;
|
|
4824
|
+
padding: 0;
|
|
4825
|
+
border: 1px solid var(--chrome-border);
|
|
4826
|
+
border-radius: 4px;
|
|
4827
|
+
background: transparent;
|
|
4828
|
+
color: var(--text-muted);
|
|
4829
|
+
font-size: 14px;
|
|
4830
|
+
line-height: 1;
|
|
4831
|
+
cursor: pointer;
|
|
4832
|
+
transition: color 120ms ease, background 120ms ease, border-color 120ms ease;
|
|
4833
|
+
flex-shrink: 0;
|
|
4834
|
+
}
|
|
4835
|
+
|
|
4836
|
+
.pinned-message-unpin:hover {
|
|
4837
|
+
color: var(--error);
|
|
4838
|
+
border-color: var(--error);
|
|
4839
|
+
background: var(--hover);
|
|
4840
|
+
}
|
|
4841
|
+
|
|
4842
|
+
.pinned-message-body {
|
|
4843
|
+
flex: 1;
|
|
4844
|
+
overflow: auto;
|
|
4845
|
+
padding: 10px 12px;
|
|
4846
|
+
font-size: 14px;
|
|
4847
|
+
line-height: 1.45;
|
|
4848
|
+
color: var(--text);
|
|
4849
|
+
white-space: pre-wrap;
|
|
4850
|
+
word-break: break-word;
|
|
4851
|
+
}
|
|
4852
|
+
|
|
4853
|
+
/* Corner resize handle — visible on hover. */
|
|
4854
|
+
.pinned-message-resize-handle {
|
|
4855
|
+
position: absolute;
|
|
4856
|
+
right: 0;
|
|
4857
|
+
bottom: 0;
|
|
4858
|
+
width: 16px;
|
|
4859
|
+
height: 16px;
|
|
4860
|
+
cursor: nwse-resize;
|
|
4861
|
+
opacity: 0;
|
|
4862
|
+
transition: opacity 120ms ease;
|
|
4863
|
+
/* Diagonal grip lines drawn with two thin gradients. */
|
|
4864
|
+
background:
|
|
4865
|
+
linear-gradient(135deg, transparent 0 45%, var(--text-muted) 45% 55%, transparent 55% 100%) no-repeat,
|
|
4866
|
+
linear-gradient(135deg, transparent 0 70%, var(--text-muted) 70% 80%, transparent 80% 100%) no-repeat;
|
|
4867
|
+
background-size: 10px 10px, 6px 6px;
|
|
4868
|
+
background-position: bottom 3px right 3px, bottom 3px right 3px;
|
|
4869
|
+
}
|
|
4870
|
+
|
|
4871
|
+
.pinned-message-panel:hover .pinned-message-resize-handle,
|
|
4872
|
+
.pinned-message-panel.resizing .pinned-message-resize-handle {
|
|
4873
|
+
opacity: 0.85;
|
|
4874
|
+
}
|
|
4875
|
+
|
|
4876
|
+
|