python-comport 0.1.0__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.
@@ -0,0 +1,51 @@
1
+ Metadata-Version: 2.4
2
+ Name: python-comport
3
+ Version: 0.1.0
4
+ Summary: Interactive arrow-key serial COM port terminal
5
+ License: MIT
6
+ Keywords: serial,com port,uart,terminal,tty
7
+ Classifier: Programming Language :: Python :: 3
8
+ Classifier: License :: OSI Approved :: MIT License
9
+ Classifier: Operating System :: OS Independent
10
+ Classifier: Environment :: Console
11
+ Classifier: Topic :: Terminals :: Serial
12
+ Requires-Python: >=3.7
13
+ Description-Content-Type: text/markdown
14
+ Requires-Dist: pyserial>=3.5
15
+
16
+ # python-comport
17
+
18
+ An interactive serial COM port terminal for the command line.
19
+
20
+ - Arrow-key menu to select the port
21
+ - Remembers your last port and baud rate — just press Enter to reconnect
22
+ - Works on Linux, macOS, and Windows
23
+ - No extra dependencies beyond `pyserial`
24
+
25
+ ## Installation
26
+
27
+ ```bash
28
+ pip install python-comport
29
+ ```
30
+
31
+ ## Usage
32
+
33
+ ```bash
34
+ comport
35
+ ```
36
+
37
+ 1. Use `↑ ↓` to select a COM port and press **Enter**
38
+ 2. Enter a baud rate (or press **Enter** to use the last saved value, default 9600)
39
+ 3. Type messages and press **Enter** to send
40
+ 4. Type `exit` or press **Ctrl+C** to quit
41
+
42
+ Settings are saved to `~/.comport-settings.json` so your last port and baud rate are pre-selected on the next run.
43
+
44
+ ## Requirements
45
+
46
+ - Python 3.7+
47
+ - pyserial
48
+
49
+ ## License
50
+
51
+ MIT
@@ -0,0 +1,36 @@
1
+ # python-comport
2
+
3
+ An interactive serial COM port terminal for the command line.
4
+
5
+ - Arrow-key menu to select the port
6
+ - Remembers your last port and baud rate — just press Enter to reconnect
7
+ - Works on Linux, macOS, and Windows
8
+ - No extra dependencies beyond `pyserial`
9
+
10
+ ## Installation
11
+
12
+ ```bash
13
+ pip install python-comport
14
+ ```
15
+
16
+ ## Usage
17
+
18
+ ```bash
19
+ comport
20
+ ```
21
+
22
+ 1. Use `↑ ↓` to select a COM port and press **Enter**
23
+ 2. Enter a baud rate (or press **Enter** to use the last saved value, default 9600)
24
+ 3. Type messages and press **Enter** to send
25
+ 4. Type `exit` or press **Ctrl+C** to quit
26
+
27
+ Settings are saved to `~/.comport-settings.json` so your last port and baud rate are pre-selected on the next run.
28
+
29
+ ## Requirements
30
+
31
+ - Python 3.7+
32
+ - pyserial
33
+
34
+ ## License
35
+
36
+ MIT
@@ -0,0 +1,27 @@
1
+ [build-system]
2
+ requires = ["setuptools>=68", "wheel"]
3
+ build-backend = "setuptools.build_meta"
4
+
5
+ [project]
6
+ name = "python-comport"
7
+ version = "0.1.0"
8
+ description = "Interactive arrow-key serial COM port terminal"
9
+ readme = "README.md"
10
+ license = { text = "MIT" }
11
+ requires-python = ">=3.7"
12
+ dependencies = ["pyserial>=3.5"]
13
+ keywords = ["serial", "com port", "uart", "terminal", "tty"]
14
+ classifiers = [
15
+ "Programming Language :: Python :: 3",
16
+ "License :: OSI Approved :: MIT License",
17
+ "Operating System :: OS Independent",
18
+ "Environment :: Console",
19
+ "Topic :: Terminals :: Serial",
20
+ ]
21
+
22
+ [project.scripts]
23
+ comport = "python_comport:main"
24
+
25
+ [tool.setuptools.packages.find]
26
+ where = ["."]
27
+ include = ["python_comport*"]
@@ -0,0 +1,175 @@
1
+ import json
2
+ import os
3
+ import sys
4
+ import threading
5
+ import time
6
+
7
+ try:
8
+ import serial
9
+ import serial.tools.list_ports
10
+ except ImportError:
11
+ print("Error: 'pyserial' library is required but not installed.")
12
+ print(" pip install pyserial")
13
+ sys.exit(1)
14
+
15
+ SETTINGS_FILE = os.path.join(os.path.expanduser("~"), ".comport-settings.json")
16
+
17
+
18
+ def load_settings():
19
+ try:
20
+ with open(SETTINGS_FILE) as f:
21
+ return json.load(f)
22
+ except Exception:
23
+ return {}
24
+
25
+
26
+ def save_settings(port, baudrate):
27
+ with open(SETTINGS_FILE, "w") as f:
28
+ json.dump({"port": port, "baudrate": baudrate}, f)
29
+
30
+
31
+ def get_key():
32
+ """Cross-platform function to detect arrow keys and Enter."""
33
+ if os.name == 'nt':
34
+ import msvcrt
35
+ key = msvcrt.getch()
36
+ if key in (b'\r', b'\n'):
37
+ return 'enter'
38
+ elif key == b'\xe0':
39
+ key2 = msvcrt.getch()
40
+ if key2 == b'H':
41
+ return 'up'
42
+ elif key2 == b'P':
43
+ return 'down'
44
+ return None
45
+ else:
46
+ import termios
47
+ import tty
48
+ fd = sys.stdin.fileno()
49
+ old_settings = termios.tcgetattr(fd)
50
+ try:
51
+ tty.setraw(fd)
52
+ ch = sys.stdin.read(1)
53
+ if ch == '\x1b':
54
+ ch2 = sys.stdin.read(1)
55
+ if ch2 == '[':
56
+ ch3 = sys.stdin.read(1)
57
+ if ch3 == 'A':
58
+ return 'up'
59
+ elif ch3 == 'B':
60
+ return 'down'
61
+ elif ch in ('\r', '\n'):
62
+ return 'enter'
63
+ return None
64
+ finally:
65
+ termios.tcsetattr(fd, termios.TCSADRAIN, old_settings)
66
+
67
+
68
+ class SimpleMenu:
69
+ """Simple arrow-key menu (no extra dependencies)."""
70
+
71
+ def __init__(self, options, default=0):
72
+ self.options = options
73
+ self.selected = default
74
+
75
+ def display(self):
76
+ os.system('cls' if os.name == 'nt' else 'clear')
77
+ print("=== Select COM Port ===")
78
+ print("Use ↑ ↓ arrow keys to move, press Enter to select.")
79
+ print("(cursor pre-set to last used port)\n")
80
+ for i, option in enumerate(self.options):
81
+ prefix = "→ " if i == self.selected else " "
82
+ print(f"{prefix}{option}")
83
+
84
+ def run(self):
85
+ while True:
86
+ self.display()
87
+ key = get_key()
88
+ if key == 'up':
89
+ self.selected = (self.selected - 1) % len(self.options)
90
+ elif key == 'down':
91
+ self.selected = (self.selected + 1) % len(self.options)
92
+ elif key == 'enter':
93
+ return self.selected
94
+
95
+
96
+ def main():
97
+ settings = load_settings()
98
+
99
+ ports = list(serial.tools.list_ports.comports())
100
+ if not ports:
101
+ print("No COM ports found on your system.")
102
+ sys.exit(1)
103
+
104
+ ports = [p for p in ports if p.description and p.description.lower() != 'n/a']
105
+ if not ports:
106
+ print("No COM ports with valid descriptions found.")
107
+ sys.exit(1)
108
+
109
+ options = [f"{p.device} — {p.description}" for p in ports]
110
+
111
+ saved_port = settings.get("port")
112
+ default_idx = next((i for i, p in enumerate(ports) if p.device == saved_port), 0)
113
+
114
+ menu = SimpleMenu(options, default=default_idx)
115
+ selected_idx = menu.run()
116
+
117
+ selected_port = ports[selected_idx].device
118
+
119
+ saved_baud = settings.get("baudrate", 9600)
120
+ baud_input = input(f"\nEnter baud rate for {selected_port} (default {saved_baud}): ").strip()
121
+ try:
122
+ baudrate = int(baud_input) if baud_input else saved_baud
123
+ except ValueError:
124
+ print(f"Invalid baud rate → using {saved_baud}")
125
+ baudrate = saved_baud
126
+
127
+ save_settings(selected_port, baudrate)
128
+
129
+ try:
130
+ ser = serial.Serial(
131
+ port=selected_port,
132
+ baudrate=baudrate,
133
+ bytesize=serial.EIGHTBITS,
134
+ parity=serial.PARITY_NONE,
135
+ stopbits=serial.STOPBITS_ONE,
136
+ timeout=0.1,
137
+ xonxoff=False,
138
+ rtscts=False,
139
+ dsrdtr=False,
140
+ )
141
+ print(f"\n✅ Connected to {selected_port} @ {baudrate} baud")
142
+ except Exception as e:
143
+ print(f"❌ Failed to open {selected_port}: {e}")
144
+ sys.exit(1)
145
+
146
+ def serial_reader():
147
+ while ser.is_open:
148
+ try:
149
+ if ser.in_waiting > 0:
150
+ data = ser.read(ser.in_waiting).decode('utf-8', errors='replace')
151
+ if data:
152
+ print(data, end='', flush=True)
153
+ except Exception:
154
+ break
155
+ time.sleep(0.01)
156
+
157
+ threading.Thread(target=serial_reader, daemon=True).start()
158
+
159
+ print("\n=== Serial Terminal Ready ===")
160
+ print("• Type your message and press Enter to send")
161
+ print("• Type 'exit' (or Ctrl+C) to quit\n")
162
+
163
+ try:
164
+ while True:
165
+ cmd = input()
166
+ if cmd.strip().lower() in ("exit", "quit"):
167
+ break
168
+ ser.write((cmd + '\r\n').encode('utf-8'))
169
+ ser.flush()
170
+ except KeyboardInterrupt:
171
+ print("\n\nInterrupted by user.")
172
+ finally:
173
+ if ser.is_open:
174
+ ser.close()
175
+ print("Serial port closed. Goodbye!")
@@ -0,0 +1,51 @@
1
+ Metadata-Version: 2.4
2
+ Name: python-comport
3
+ Version: 0.1.0
4
+ Summary: Interactive arrow-key serial COM port terminal
5
+ License: MIT
6
+ Keywords: serial,com port,uart,terminal,tty
7
+ Classifier: Programming Language :: Python :: 3
8
+ Classifier: License :: OSI Approved :: MIT License
9
+ Classifier: Operating System :: OS Independent
10
+ Classifier: Environment :: Console
11
+ Classifier: Topic :: Terminals :: Serial
12
+ Requires-Python: >=3.7
13
+ Description-Content-Type: text/markdown
14
+ Requires-Dist: pyserial>=3.5
15
+
16
+ # python-comport
17
+
18
+ An interactive serial COM port terminal for the command line.
19
+
20
+ - Arrow-key menu to select the port
21
+ - Remembers your last port and baud rate — just press Enter to reconnect
22
+ - Works on Linux, macOS, and Windows
23
+ - No extra dependencies beyond `pyserial`
24
+
25
+ ## Installation
26
+
27
+ ```bash
28
+ pip install python-comport
29
+ ```
30
+
31
+ ## Usage
32
+
33
+ ```bash
34
+ comport
35
+ ```
36
+
37
+ 1. Use `↑ ↓` to select a COM port and press **Enter**
38
+ 2. Enter a baud rate (or press **Enter** to use the last saved value, default 9600)
39
+ 3. Type messages and press **Enter** to send
40
+ 4. Type `exit` or press **Ctrl+C** to quit
41
+
42
+ Settings are saved to `~/.comport-settings.json` so your last port and baud rate are pre-selected on the next run.
43
+
44
+ ## Requirements
45
+
46
+ - Python 3.7+
47
+ - pyserial
48
+
49
+ ## License
50
+
51
+ MIT
@@ -0,0 +1,9 @@
1
+ README.md
2
+ pyproject.toml
3
+ python_comport/__init__.py
4
+ python_comport.egg-info/PKG-INFO
5
+ python_comport.egg-info/SOURCES.txt
6
+ python_comport.egg-info/dependency_links.txt
7
+ python_comport.egg-info/entry_points.txt
8
+ python_comport.egg-info/requires.txt
9
+ python_comport.egg-info/top_level.txt
@@ -0,0 +1,2 @@
1
+ [console_scripts]
2
+ comport = python_comport:main
@@ -0,0 +1 @@
1
+ pyserial>=3.5
@@ -0,0 +1 @@
1
+ python_comport
@@ -0,0 +1,4 @@
1
+ [egg_info]
2
+ tag_build =
3
+ tag_date = 0
4
+