portacode 0.3.17.dev2__tar.gz → 0.3.18.dev0__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.
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/PKG-INFO +1 -1
- portacode-0.3.18.dev0/portacode/_version.py +34 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/handlers/project_state_handlers.py +61 -11
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode.egg-info/PKG-INFO +1 -1
- portacode-0.3.17.dev2/portacode/_version.py +0 -21
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/.claude/agents/communication-manager.md +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/.claude/settings.local.json +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/.gitignore +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/.gitmodules +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/LICENSE +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/MANIFEST.in +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/Makefile +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/README.md +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/backup.sh +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/docker-compose.yaml +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/README.md +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/__init__.py +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/__main__.py +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/cli.py +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/README.md +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/__init__.py +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/client.py +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/handlers/README.md +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/handlers/WEBSOCKET_PROTOCOL.md +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/handlers/__init__.py +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/handlers/base.py +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/handlers/file_handlers.py +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/handlers/registry.py +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/handlers/session.py +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/handlers/system_handlers.py +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/handlers/tab_factory.py +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/handlers/terminal_handlers.py +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/multiplex.py +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/terminal.py +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/data.py +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/keypair.py +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/service.py +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode.egg-info/SOURCES.txt +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode.egg-info/dependency_links.txt +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode.egg-info/entry_points.txt +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode.egg-info/requires.txt +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode.egg-info/top_level.txt +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/pyproject.toml +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/restore.sh +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/setup.cfg +0 -0
- {portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/setup.py +0 -0
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
# file generated by setuptools-scm
|
|
2
|
+
# don't change, don't track in version control
|
|
3
|
+
|
|
4
|
+
__all__ = [
|
|
5
|
+
"__version__",
|
|
6
|
+
"__version_tuple__",
|
|
7
|
+
"version",
|
|
8
|
+
"version_tuple",
|
|
9
|
+
"__commit_id__",
|
|
10
|
+
"commit_id",
|
|
11
|
+
]
|
|
12
|
+
|
|
13
|
+
TYPE_CHECKING = False
|
|
14
|
+
if TYPE_CHECKING:
|
|
15
|
+
from typing import Tuple
|
|
16
|
+
from typing import Union
|
|
17
|
+
|
|
18
|
+
VERSION_TUPLE = Tuple[Union[int, str], ...]
|
|
19
|
+
COMMIT_ID = Union[str, None]
|
|
20
|
+
else:
|
|
21
|
+
VERSION_TUPLE = object
|
|
22
|
+
COMMIT_ID = object
|
|
23
|
+
|
|
24
|
+
version: str
|
|
25
|
+
__version__: str
|
|
26
|
+
__version_tuple__: VERSION_TUPLE
|
|
27
|
+
version_tuple: VERSION_TUPLE
|
|
28
|
+
commit_id: COMMIT_ID
|
|
29
|
+
__commit_id__: COMMIT_ID
|
|
30
|
+
|
|
31
|
+
__version__ = version = '0.3.18.dev0'
|
|
32
|
+
__version_tuple__ = version_tuple = (0, 3, 18, 'dev0')
|
|
33
|
+
|
|
34
|
+
__commit_id__ = commit_id = None
|
|
@@ -465,11 +465,6 @@ class FileSystemWatcher:
|
|
|
465
465
|
super().__init__()
|
|
466
466
|
|
|
467
467
|
def on_any_event(self, event):
|
|
468
|
-
# Skip events for .git folder and its contents to avoid noise
|
|
469
|
-
path_parts = Path(event.src_path).parts
|
|
470
|
-
if '.git' in path_parts:
|
|
471
|
-
return
|
|
472
|
-
|
|
473
468
|
# Skip debug files to avoid feedback loops
|
|
474
469
|
if event.src_path.endswith('project_state_debug.json'):
|
|
475
470
|
return
|
|
@@ -479,7 +474,33 @@ class FileSystemWatcher:
|
|
|
479
474
|
if event.event_type in ('opened', 'closed'):
|
|
480
475
|
return
|
|
481
476
|
|
|
482
|
-
|
|
477
|
+
# Handle .git folder events separately for git status monitoring
|
|
478
|
+
path_parts = Path(event.src_path).parts
|
|
479
|
+
if '.git' in path_parts:
|
|
480
|
+
# Get the relative path within .git directory
|
|
481
|
+
try:
|
|
482
|
+
git_index = path_parts.index('.git')
|
|
483
|
+
git_relative_path = '/'.join(path_parts[git_index + 1:])
|
|
484
|
+
git_file = Path(event.src_path).name
|
|
485
|
+
|
|
486
|
+
# Monitor git files that indicate repository state changes
|
|
487
|
+
should_monitor_git_file = (
|
|
488
|
+
git_file == 'index' or # Staging area changes
|
|
489
|
+
git_file == 'HEAD' or # Branch switches
|
|
490
|
+
git_relative_path.startswith('refs/heads/') or # Branch updates
|
|
491
|
+
git_relative_path.startswith('refs/remotes/') or # Remote tracking branches
|
|
492
|
+
git_relative_path.startswith('logs/refs/heads/') or # Branch history
|
|
493
|
+
git_relative_path.startswith('logs/HEAD') # HEAD history
|
|
494
|
+
)
|
|
495
|
+
|
|
496
|
+
if should_monitor_git_file:
|
|
497
|
+
logger.info("Git status change detected: %s - %s", event.event_type, event.src_path)
|
|
498
|
+
else:
|
|
499
|
+
return # Skip other .git files
|
|
500
|
+
except (ValueError, IndexError):
|
|
501
|
+
return # Skip if can't parse .git path
|
|
502
|
+
else:
|
|
503
|
+
logger.info("File system event: %s - %s", event.event_type, event.src_path)
|
|
483
504
|
|
|
484
505
|
# Schedule async task in the main event loop from this watchdog thread
|
|
485
506
|
if self.watcher.event_loop and not self.watcher.event_loop.is_closed():
|
|
@@ -503,11 +524,6 @@ class FileSystemWatcher:
|
|
|
503
524
|
logger.warning("Watchdog not available, cannot start watching: %s", path)
|
|
504
525
|
return
|
|
505
526
|
|
|
506
|
-
# Extra safety check: never watch .git folders
|
|
507
|
-
if Path(path).name == '.git':
|
|
508
|
-
logger.debug("Refusing to watch .git folder: %s", path)
|
|
509
|
-
return
|
|
510
|
-
|
|
511
527
|
if path not in self.watched_paths:
|
|
512
528
|
try:
|
|
513
529
|
# Use recursive=False to watch only direct contents of each folder
|
|
@@ -523,6 +539,27 @@ class FileSystemWatcher:
|
|
|
523
539
|
else:
|
|
524
540
|
logger.debug("Path already being watched: %s", path)
|
|
525
541
|
|
|
542
|
+
def start_watching_git_directory(self, git_path: str):
|
|
543
|
+
"""Start watching a .git directory for git status changes."""
|
|
544
|
+
if not WATCHDOG_AVAILABLE or not self.observer:
|
|
545
|
+
logger.warning("Watchdog not available, cannot start watching git directory: %s", git_path)
|
|
546
|
+
return
|
|
547
|
+
|
|
548
|
+
if git_path not in self.watched_paths:
|
|
549
|
+
try:
|
|
550
|
+
# Watch .git directory recursively to catch changes in refs/, logs/, etc.
|
|
551
|
+
self.observer.schedule(self.event_handler, git_path, recursive=True)
|
|
552
|
+
self.watched_paths.add(git_path)
|
|
553
|
+
logger.info("Started watching git directory (recursive): %s", git_path)
|
|
554
|
+
|
|
555
|
+
if not self.observer.is_alive():
|
|
556
|
+
self.observer.start()
|
|
557
|
+
logger.info("Started file system observer")
|
|
558
|
+
except Exception as e:
|
|
559
|
+
logger.error("Error starting git directory watcher for %s: %s", git_path, e)
|
|
560
|
+
else:
|
|
561
|
+
logger.debug("Git directory already being watched: %s", git_path)
|
|
562
|
+
|
|
526
563
|
def stop_watching(self, path: str):
|
|
527
564
|
"""Stop watching a specific path."""
|
|
528
565
|
if not WATCHDOG_AVAILABLE or not self.observer:
|
|
@@ -673,6 +710,13 @@ class ProjectStateManager:
|
|
|
673
710
|
for monitored_folder in project_state.monitored_folders:
|
|
674
711
|
self.file_watcher.start_watching(monitored_folder.folder_path)
|
|
675
712
|
|
|
713
|
+
# For git repositories, also watch the .git directory for git status changes
|
|
714
|
+
if project_state.is_git_repo:
|
|
715
|
+
git_dir_path = os.path.join(project_state.project_folder_path, '.git')
|
|
716
|
+
if os.path.exists(git_dir_path):
|
|
717
|
+
self.file_watcher.start_watching_git_directory(git_dir_path)
|
|
718
|
+
logger.debug("Started monitoring .git directory for git status changes: %s", git_dir_path)
|
|
719
|
+
|
|
676
720
|
logger.debug("Watchdog synchronized: watching %d monitored folders individually", len(project_state.monitored_folders))
|
|
677
721
|
|
|
678
722
|
async def _sync_all_state_with_monitored_folders(self, project_state: ProjectState):
|
|
@@ -1196,6 +1240,7 @@ class ProjectStateManager:
|
|
|
1196
1240
|
|
|
1197
1241
|
# Update Git status
|
|
1198
1242
|
if git_manager:
|
|
1243
|
+
project_state.git_branch = git_manager.get_branch_name()
|
|
1199
1244
|
project_state.git_status_summary = git_manager.get_status_summary()
|
|
1200
1245
|
project_state.git_detailed_status = git_manager.get_detailed_status()
|
|
1201
1246
|
|
|
@@ -1268,6 +1313,11 @@ class ProjectStateManager:
|
|
|
1268
1313
|
for monitored_folder in project_state.monitored_folders:
|
|
1269
1314
|
self.file_watcher.stop_watching(monitored_folder.folder_path)
|
|
1270
1315
|
|
|
1316
|
+
# Stop watching .git directory if it was being monitored
|
|
1317
|
+
if project_state.is_git_repo:
|
|
1318
|
+
git_dir_path = os.path.join(project_state.project_folder_path, '.git')
|
|
1319
|
+
self.file_watcher.stop_watching(git_dir_path)
|
|
1320
|
+
|
|
1271
1321
|
# Clean up managers
|
|
1272
1322
|
self.git_managers.pop(client_session_key, None)
|
|
1273
1323
|
self.projects.pop(client_session_key, None)
|
|
@@ -1,21 +0,0 @@
|
|
|
1
|
-
# file generated by setuptools-scm
|
|
2
|
-
# don't change, don't track in version control
|
|
3
|
-
|
|
4
|
-
__all__ = ["__version__", "__version_tuple__", "version", "version_tuple"]
|
|
5
|
-
|
|
6
|
-
TYPE_CHECKING = False
|
|
7
|
-
if TYPE_CHECKING:
|
|
8
|
-
from typing import Tuple
|
|
9
|
-
from typing import Union
|
|
10
|
-
|
|
11
|
-
VERSION_TUPLE = Tuple[Union[int, str], ...]
|
|
12
|
-
else:
|
|
13
|
-
VERSION_TUPLE = object
|
|
14
|
-
|
|
15
|
-
version: str
|
|
16
|
-
__version__: str
|
|
17
|
-
__version_tuple__: VERSION_TUPLE
|
|
18
|
-
version_tuple: VERSION_TUPLE
|
|
19
|
-
|
|
20
|
-
__version__ = version = '0.3.17.dev2'
|
|
21
|
-
__version_tuple__ = version_tuple = (0, 3, 17, 'dev2')
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/handlers/WEBSOCKET_PROTOCOL.md
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/handlers/file_handlers.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/handlers/system_handlers.py
RENAMED
|
File without changes
|
{portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/handlers/tab_factory.py
RENAMED
|
File without changes
|
{portacode-0.3.17.dev2 → portacode-0.3.18.dev0}/portacode/connection/handlers/terminal_handlers.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|