portacode 0.3.3.dev0__tar.gz → 0.3.4.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.
Files changed (38) hide show
  1. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/PKG-INFO +1 -1
  2. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/_version.py +2 -2
  3. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/connection/handlers/session.py +8 -92
  4. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode.egg-info/PKG-INFO +1 -1
  5. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/.gitignore +0 -0
  6. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/.gitmodules +0 -0
  7. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/LICENSE +0 -0
  8. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/MANIFEST.in +0 -0
  9. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/Makefile +0 -0
  10. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/README.md +0 -0
  11. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/docker-compose.yaml +0 -0
  12. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/README.md +0 -0
  13. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/__init__.py +0 -0
  14. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/__main__.py +0 -0
  15. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/cli.py +0 -0
  16. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/connection/README.md +0 -0
  17. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/connection/__init__.py +0 -0
  18. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/connection/client.py +0 -0
  19. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/connection/handlers/README.md +0 -0
  20. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/connection/handlers/__init__.py +0 -0
  21. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/connection/handlers/base.py +0 -0
  22. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/connection/handlers/file_handlers.py +0 -0
  23. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/connection/handlers/registry.py +0 -0
  24. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/connection/handlers/system_handlers.py +0 -0
  25. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/connection/handlers/terminal_handlers.py +0 -0
  26. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/connection/multiplex.py +0 -0
  27. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/connection/terminal.py +0 -0
  28. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/data.py +0 -0
  29. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/keypair.py +0 -0
  30. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode/service.py +0 -0
  31. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode.egg-info/SOURCES.txt +0 -0
  32. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode.egg-info/dependency_links.txt +0 -0
  33. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode.egg-info/entry_points.txt +0 -0
  34. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode.egg-info/requires.txt +0 -0
  35. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/portacode.egg-info/top_level.txt +0 -0
  36. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/pyproject.toml +0 -0
  37. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/setup.cfg +0 -0
  38. {portacode-0.3.3.dev0 → portacode-0.3.4.dev0}/setup.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: portacode
3
- Version: 0.3.3.dev0
3
+ Version: 0.3.4.dev0
4
4
  Summary: Portacode CLI client and SDK
5
5
  Home-page: https://github.com/portacode/portacode
6
6
  Author: Meena Erian
@@ -17,5 +17,5 @@ __version__: str
17
17
  __version_tuple__: VERSION_TUPLE
18
18
  version_tuple: VERSION_TUPLE
19
19
 
20
- __version__ = version = '0.3.3.dev'
21
- __version_tuple__ = version_tuple = (0, 3, 3, 'dev0')
20
+ __version__ = version = '0.3.4.dev'
21
+ __version_tuple__ = version_tuple = (0, 3, 4, 'dev0')
@@ -10,14 +10,6 @@ from pathlib import Path
10
10
  from typing import Any, Dict, Optional, List, TYPE_CHECKING
11
11
  from collections import deque
12
12
 
13
- # Terminal control imports (only available on Unix)
14
- try:
15
- import termios
16
- import tty
17
- _HAS_TERMIOS = True
18
- except ImportError:
19
- _HAS_TERMIOS = False
20
-
21
13
  if TYPE_CHECKING:
22
14
  from ..multiplex import Channel
23
15
 
@@ -29,15 +21,6 @@ _IS_WINDOWS = sys.platform.startswith("win")
29
21
  _DEFAULT_ENV = {
30
22
  "TERM": "xterm-256color",
31
23
  "LANG": "C.UTF-8",
32
- # Add additional terminal environment variables for better compatibility
33
- "COLUMNS": "80",
34
- "LINES": "24",
35
- "PS1": r'\u@\h:\w\$ ', # Standard bash prompt
36
- "HISTSIZE": "1000",
37
- "HISTFILESIZE": "2000",
38
- # Ensure proper terminal behavior
39
- "DEBIAN_FRONTEND": "noninteractive", # Prevent interactive prompts
40
- "TERM_PROGRAM": "portacode",
41
24
  }
42
25
 
43
26
 
@@ -46,12 +29,6 @@ def _build_child_env() -> Dict[str, str]:
46
29
  env = os.environ.copy()
47
30
  for k, v in _DEFAULT_ENV.items():
48
31
  env.setdefault(k, v)
49
-
50
- # Ensure SSH_TTY is not set when using pipes to avoid shell confusion
51
- if "SSH_TTY" in env:
52
- logger.debug("Removing SSH_TTY from environment to prevent shell confusion")
53
- del env["SSH_TTY"]
54
-
55
32
  return env
56
33
 
57
34
 
@@ -213,19 +190,17 @@ class SessionManager:
213
190
  channel_id = self._allocate_channel_id()
214
191
  channel = self.mux.get_channel(channel_id)
215
192
 
216
- # Choose shell - prefer bash over sh for better compatibility
193
+ # Choose shell - prefer bash over sh for better terminal compatibility
217
194
  if shell is None:
218
195
  if not _IS_WINDOWS:
219
- # Try to use bash if available, fallback to default shell
220
196
  shell = os.getenv("SHELL")
221
- if shell is None or shell == "/bin/sh":
222
- # Try to find bash
197
+ # If the default shell is /bin/sh, try to use bash instead for better terminal support
198
+ if shell == "/bin/sh":
223
199
  for bash_path in ["/bin/bash", "/usr/bin/bash", "/usr/local/bin/bash"]:
224
200
  if os.path.exists(bash_path):
225
201
  shell = bash_path
202
+ logger.info("Switching from /bin/sh to %s for better terminal compatibility", shell)
226
203
  break
227
- else:
228
- shell = "/bin/sh"
229
204
  else:
230
205
  shell = os.getenv("COMSPEC", "cmd.exe")
231
206
 
@@ -242,30 +217,9 @@ class SessionManager:
242
217
  session = WindowsTerminalSession(term_id, pty_proc, channel)
243
218
  else:
244
219
  # Unix: try real PTY for proper TTY semantics
245
- pty_success = False
246
220
  try:
247
221
  import pty
248
-
249
- logger.debug("Attempting to allocate PTY for terminal %s", term_id)
250
222
  master_fd, slave_fd = pty.openpty()
251
-
252
- # Set terminal attributes for better compatibility
253
- if _HAS_TERMIOS:
254
- try:
255
- # Get current terminal settings
256
- attrs = termios.tcgetattr(slave_fd)
257
- # Enable canonical mode and echo
258
- attrs[3] |= termios.ICANON | termios.ECHO | termios.ECHOE | termios.ECHOK
259
- # Set input and output modes
260
- attrs[0] |= termios.ICRNL # Map CR to NL on input
261
- attrs[1] |= termios.OPOST | termios.ONLCR # Map NL to CR-NL on output
262
- termios.tcsetattr(slave_fd, termios.TCSANOW, attrs)
263
- logger.debug("Successfully configured terminal attributes")
264
- except Exception as e:
265
- logger.warning("Failed to configure terminal attributes: %s", e)
266
- else:
267
- logger.debug("termios not available, skipping terminal attribute configuration")
268
-
269
223
  proc = await asyncio.create_subprocess_exec(
270
224
  shell,
271
225
  stdin=slave_fd,
@@ -275,10 +229,6 @@ class SessionManager:
275
229
  cwd=cwd,
276
230
  env=_build_child_env(),
277
231
  )
278
-
279
- # Close slave_fd in parent process
280
- os.close(slave_fd)
281
-
282
232
  # Wrap master_fd into a StreamReader
283
233
  loop = asyncio.get_running_loop()
284
234
  reader = asyncio.StreamReader()
@@ -290,49 +240,16 @@ class SessionManager:
290
240
  lambda: asyncio.Protocol(), os.fdopen(master_fd, "wb", buffering=0)
291
241
  )
292
242
  proc.stdin = asyncio.StreamWriter(writer_transport, writer_protocol, reader, loop)
293
-
294
- pty_success = True
295
- logger.info("Successfully allocated PTY for terminal %s", term_id)
296
-
297
- except Exception as e:
298
- logger.warning("Failed to allocate PTY for terminal %s: %s", term_id, e)
299
-
300
- # Enhanced fallback with proper shell invocation
301
- logger.info("Using enhanced pipe fallback for terminal %s", term_id)
302
-
303
- # Create enhanced environment for pipe mode
304
- pipe_env = _build_child_env()
305
- pipe_env["TERM"] = "dumb" # Use dumb terminal for pipes
306
- pipe_env["PS1"] = "$ " # Simple prompt for pipes
307
-
308
- # Use shell with explicit interactive and login flags
309
- shell_args = [shell]
310
- if shell.endswith("bash"):
311
- shell_args.extend(["-i", "-l"]) # Interactive and login shell
312
- elif shell.endswith("sh"):
313
- shell_args.extend(["-i"]) # Interactive shell
314
-
243
+ except Exception:
244
+ logger.warning("Failed to allocate PTY, falling back to pipes")
315
245
  proc = await asyncio.create_subprocess_exec(
316
- *shell_args,
246
+ shell,
317
247
  stdin=asyncio.subprocess.PIPE,
318
248
  stdout=asyncio.subprocess.PIPE,
319
249
  stderr=asyncio.subprocess.STDOUT,
320
250
  cwd=cwd,
321
- env=pipe_env,
251
+ env=_build_child_env(),
322
252
  )
323
-
324
- # Send initial command to set up better terminal behavior
325
- if proc.stdin:
326
- initial_setup = (
327
- "stty -echo 2>/dev/null || true\n" # Disable echo to prevent double output
328
- "set +o posix 2>/dev/null || true\n" # Disable POSIX mode if possible
329
- "PS1='$ '\n" # Set simple prompt
330
- "export PS1\n"
331
- "clear 2>/dev/null || echo 'Terminal ready'\n"
332
- )
333
- proc.stdin.write(initial_setup.encode())
334
- await proc.stdin.drain()
335
-
336
253
  session = TerminalSession(term_id, proc, channel)
337
254
 
338
255
  self._sessions[term_id] = session
@@ -344,7 +261,6 @@ class SessionManager:
344
261
  "pid": session.proc.pid,
345
262
  "shell": shell,
346
263
  "cwd": cwd,
347
- "pty_mode": pty_success if not _IS_WINDOWS else True,
348
264
  }
349
265
 
350
266
  def get_session(self, terminal_id: str) -> Optional[TerminalSession]:
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: portacode
3
- Version: 0.3.3.dev0
3
+ Version: 0.3.4.dev0
4
4
  Summary: Portacode CLI client and SDK
5
5
  Home-page: https://github.com/portacode/portacode
6
6
  Author: Meena Erian
File without changes
File without changes
File without changes
File without changes
File without changes