ngpt 3.5.2__py3-none-any.whl → 3.5.4__py3-none-any.whl

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.
ngpt/cli/modes/code.py CHANGED
@@ -1,6 +1,6 @@
1
1
  from ..formatters import COLORS
2
2
  from ..renderers import prettify_markdown, prettify_streaming_markdown, has_markdown_renderer, show_available_renderers
3
- from ..ui import spinner
3
+ from ..ui import spinner, copy_to_clipboard
4
4
  from ...utils import enhance_prompt_with_web_search
5
5
  import sys
6
6
  import threading
@@ -298,4 +298,8 @@ def code_mode(client, args, logger=None):
298
298
  prettify_markdown(generated_code, args.renderer)
299
299
  else:
300
300
  # Should only happen if --no-stream was used without prettify
301
- print(f"\nGenerated code:\n{generated_code}")
301
+ print(f"\nGenerated code:\n{generated_code}")
302
+
303
+ # Offer to copy to clipboard
304
+ if generated_code and not args.no_stream:
305
+ copy_to_clipboard(generated_code)
@@ -8,7 +8,7 @@ import threading
8
8
  from datetime import datetime
9
9
  import logging
10
10
  from ..formatters import COLORS
11
- from ..ui import spinner
11
+ from ..ui import spinner, copy_to_clipboard
12
12
  from ...utils.log import create_gitcommsg_logger
13
13
  from ...utils.cli_config import get_cli_config_option
14
14
 
@@ -1128,15 +1128,9 @@ def gitcommsg_mode(client, args, logger=None):
1128
1128
  active_logger.log_content("INFO", "FINAL_COMMIT_MESSAGE", result)
1129
1129
 
1130
1130
  # Try to copy to clipboard
1131
- try:
1132
- import pyperclip
1133
- pyperclip.copy(result)
1134
- print(f"\n{COLORS['green']}(Copied to clipboard){COLORS['reset']}")
1135
- if active_logger:
1136
- active_logger.info("Commit message copied to clipboard")
1137
- except ImportError:
1138
- if active_logger:
1139
- active_logger.debug("pyperclip not available, couldn't copy to clipboard")
1131
+ copy_to_clipboard(result)
1132
+ if active_logger:
1133
+ active_logger.info("Offered to copy commit message to clipboard")
1140
1134
 
1141
1135
  except Exception as e:
1142
1136
  print(f"{COLORS['red']}Error: {str(e)}{COLORS['reset']}")
ngpt/cli/modes/rewrite.py CHANGED
@@ -1,10 +1,9 @@
1
1
  import sys
2
- import platform
3
2
  import threading
4
3
  import time
5
4
  from ..formatters import COLORS
6
5
  from ..renderers import prettify_markdown, prettify_streaming_markdown
7
- from ..ui import get_multiline_input, spinner
6
+ from ..ui import get_multiline_input, spinner, copy_to_clipboard
8
7
  from ...utils import enhance_prompt_with_web_search
9
8
 
10
9
  # System prompt for rewriting text
@@ -71,28 +70,6 @@ ORIGINAL: "The user interface, which is built using React, Redux, and various ot
71
70
  BETTER: "The React/Redux user interface needs redesigning to accommodate our planned new features."
72
71
  """
73
72
 
74
- def get_terminal_input():
75
- """Get input from terminal in a cross-platform way, even when stdin is redirected."""
76
- if platform.system() == 'Windows':
77
- # Windows-specific solution
78
- try:
79
- import msvcrt
80
- sys.stdout.flush()
81
- # Wait for a keypress
82
- char = msvcrt.getch().decode('utf-8').lower()
83
- print(char) # Echo the character
84
- return char
85
- except ImportError:
86
- # Fallback if msvcrt is not available
87
- return None
88
- else:
89
- # Unix-like systems (Linux, macOS)
90
- try:
91
- with open('/dev/tty', 'r') as tty:
92
- return tty.readline().strip().lower()
93
- except (IOError, OSError):
94
- return None
95
-
96
73
  def rewrite_mode(client, args, logger=None):
97
74
  """Handle the text rewriting mode.
98
75
 
@@ -267,24 +244,5 @@ def rewrite_mode(client, args, logger=None):
267
244
  print(response)
268
245
 
269
246
  # Offer to copy to clipboard if not in a redirected output
270
- if not args.no_stream and sys.stdout.isatty():
271
- try:
272
- # Make sure to flush output before asking for input
273
- # Make the prompt more visible with colors and formatting
274
- clipboard_prompt = f"{COLORS['cyan']}{COLORS['bold']}Copy to clipboard? (y/n){COLORS['reset']} "
275
- print(clipboard_prompt, end="")
276
- sys.stdout.flush()
277
-
278
- # Cross-platform terminal input
279
- answer = get_terminal_input()
280
-
281
- if answer == 'y':
282
- try:
283
- import pyperclip
284
- pyperclip.copy(response)
285
- print(f"{COLORS['green']}Copied to clipboard.{COLORS['reset']}")
286
- except ImportError:
287
- print(f"{COLORS['yellow']}pyperclip not installed. Try: pip install \"ngpt[clipboard]\" {COLORS['reset']}")
288
-
289
- except (KeyboardInterrupt, EOFError):
290
- pass
247
+ if not args.no_stream and response:
248
+ copy_to_clipboard(response)
ngpt/cli/ui.py CHANGED
@@ -1,6 +1,7 @@
1
1
  import sys
2
2
  import time
3
3
  import shutil
4
+ import platform
4
5
  from .formatters import COLORS
5
6
 
6
7
  # Optional imports for enhanced UI
@@ -155,6 +156,68 @@ def get_multiline_input():
155
156
  print("\nInput cancelled by user. Exiting gracefully.")
156
157
  return None
157
158
 
159
+ def get_terminal_input():
160
+ """Get input from terminal in a cross-platform way, even when stdin is redirected."""
161
+ if platform.system() == 'Windows':
162
+ # Windows-specific solution
163
+ try:
164
+ import msvcrt
165
+ sys.stdout.flush()
166
+ # Wait for a keypress
167
+ char = msvcrt.getch().decode('utf-8').lower()
168
+ print(char) # Echo the character
169
+ return char
170
+ except ImportError:
171
+ # Fallback if msvcrt is not available
172
+ return None
173
+ else:
174
+ # Unix-like systems (Linux, macOS)
175
+ try:
176
+ with open('/dev/tty', 'r') as tty:
177
+ return tty.readline().strip().lower()
178
+ except (IOError, OSError):
179
+ return None
180
+
181
+ def copy_to_clipboard(content, prompt_message=None):
182
+ """Copy content to clipboard with user confirmation.
183
+
184
+ Args:
185
+ content: The text content to copy to clipboard
186
+ prompt_message: Optional custom message for the prompt (default: "Copy to clipboard? (y/n)")
187
+
188
+ Returns:
189
+ bool: True if copied to clipboard successfully, False otherwise
190
+ """
191
+ # Only prompt if stdout is connected to a terminal
192
+ if not sys.stdout.isatty():
193
+ return False
194
+
195
+ try:
196
+ # Default prompt message
197
+ if prompt_message is None:
198
+ prompt_message = "Copy to clipboard? (y/n)"
199
+
200
+ # Make the prompt more visible with colors and formatting
201
+ clipboard_prompt = f"{COLORS['cyan']}{COLORS['bold']}{prompt_message}{COLORS['reset']} "
202
+ print(clipboard_prompt, end="")
203
+ sys.stdout.flush()
204
+
205
+ # Cross-platform terminal input
206
+ answer = get_terminal_input()
207
+
208
+ if answer == 'y':
209
+ try:
210
+ import pyperclip
211
+ pyperclip.copy(content)
212
+ print(f"{COLORS['green']}Copied to clipboard.{COLORS['reset']}")
213
+ return True
214
+ except ImportError:
215
+ print(f"{COLORS['yellow']}pyperclip not installed. Try: pip install \"ngpt[clipboard]\" {COLORS['reset']}")
216
+ return False
217
+ return False
218
+ except (KeyboardInterrupt, EOFError):
219
+ return False
220
+
158
221
  def spinner(message, duration=5, spinner_chars="⣾⣽⣻⢿⡿⣟⣯⣷", color=None, stop_event=None, clean_exit=False):
159
222
  """Display a spinner animation with a message.
160
223
 
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: ngpt
3
- Version: 3.5.2
3
+ Version: 3.5.4
4
4
  Summary: Swiss army knife for LLMs: powerful CLI and interactive chatbot in one package. Seamlessly work with OpenAI, Ollama, Groq, Claude, Gemini, or any OpenAI-compatible API to generate code, craft git commits, rewrite text, and execute shell commands.
5
5
  Project-URL: Homepage, https://github.com/nazdridoy/ngpt
6
6
  Project-URL: Repository, https://github.com/nazdridoy/ngpt
@@ -54,7 +54,7 @@ Description-Content-Type: text/markdown
54
54
  🤖 nGPT: A Swiss army knife for LLMs: powerful CLI and interactive chatbot in one package. Seamlessly work with OpenAI, Ollama, Groq, Claude, Gemini, or any OpenAI-compatible API to generate code, craft git commits, rewrite text, and execute shell commands. Fast, lightweight, and designed for both casual users and developers.
55
55
 
56
56
 
57
- ![2025-04-23_16-18-01](https://github.com/user-attachments/assets/b8e58926-5165-4352-b48b-9f4a982da86e)
57
+ ![ngpt-i](https://raw.githubusercontent.com/nazdridoy/ngpt/main/previews/ngpt-i.png)
58
58
 
59
59
 
60
60
  ## Features
@@ -7,13 +7,13 @@ ngpt/cli/config_manager.py,sha256=NQQcWnjUppAAd0s0p9YAf8EyKS1ex5-0EB4DvKdB4dk,36
7
7
  ngpt/cli/formatters.py,sha256=HBYGlx_7eoAKyzfy0Vq5L0yn8yVKjngqYBukMmXCcz0,9401
8
8
  ngpt/cli/main.py,sha256=oKX7ryTIrsvQRJHVnH2a763pGyNZthq81wkrRILwHLw,28932
9
9
  ngpt/cli/renderers.py,sha256=m71BeUXKynpKKGXFzwRSW1XngvyKiZ_xEsdujUbU0MA,16597
10
- ngpt/cli/ui.py,sha256=HoHDFpLiwMBP5wtMb8YYo244FMiqiPFRoBNcNGp6N0A,7310
10
+ ngpt/cli/ui.py,sha256=5is8RiYEDB4W2YYwaA4V1-2RojuKeRofrKbQRfSguHM,9545
11
11
  ngpt/cli/modes/__init__.py,sha256=KP7VR6Xw9k1p5Jcu0F38RDxSFvFIzH3j1ThDLNwznUI,363
12
12
  ngpt/cli/modes/chat.py,sha256=jfKkrtSkx1gKPsKXDMxZ7BiJiMsCtFHyZCGIdmNQ0fk,7816
13
- ngpt/cli/modes/code.py,sha256=VYpAHXNLDmrOznTIy4XgQPM7gunSnw3VorvrjPG_1Wg,12359
14
- ngpt/cli/modes/gitcommsg.py,sha256=rsfMoeOupmNp-5p5fsMSPAf18BbzXWq-4PF2HjEz6SY,46991
13
+ ngpt/cli/modes/code.py,sha256=3avR9OM-D3r4HHfVm2bTfCOlsYQoqgtvU49zGzYfUqw,12513
14
+ ngpt/cli/modes/gitcommsg.py,sha256=Alm1OLxXkuteiDSnDxjmnPvlSggGG2sTlUBAqJaYaN4,46739
15
15
  ngpt/cli/modes/interactive.py,sha256=TtBrZUX45CVfKOPvkb1ya7dIQhXLILtn7ajmfM9ohso,17419
16
- ngpt/cli/modes/rewrite.py,sha256=9o37-o5Q8SGfJ91-8pD4h7d5RsJeu85OEdv3nXKzQiA,12361
16
+ ngpt/cli/modes/rewrite.py,sha256=EKCPZwvu0MTDpD-nj_oty8vjVQpaF4ucwmTG99LJT6M,10736
17
17
  ngpt/cli/modes/shell.py,sha256=FaFOzxTxPJCpYsiQJIttS69fZg-asV4LVA5TLaGVN0Y,8897
18
18
  ngpt/cli/modes/text.py,sha256=7t5WWXMFxGkBM5HMP4irbN9aQwxE2YgywjiVPep710k,6417
19
19
  ngpt/utils/__init__.py,sha256=qu_66I1Vtav2f1LDiPn5J3DUsbK7o1CSScMcTkYqxoM,1179
@@ -21,8 +21,8 @@ ngpt/utils/cli_config.py,sha256=Ug8cECBTIuzOwkBWidLTfs-OAdOsCMJ2bNa70pOADfw,1119
21
21
  ngpt/utils/config.py,sha256=wsArA4osnh8fKqOvtsPqqBxAz3DpdjtaWUFaRtnUdyc,10452
22
22
  ngpt/utils/log.py,sha256=f1jg2iFo35PAmsarH8FVL_62plq4VXH0Mu2QiP6RJGw,15934
23
23
  ngpt/utils/web_search.py,sha256=w5ke4KJMRxq7r5jtbUXvspja6XhjoPZloVkZ0IvBXIE,30731
24
- ngpt-3.5.2.dist-info/METADATA,sha256=sC8YBnPKWY39E1CMiaYzcxW5JWMWkPOoZ05K8KgspuQ,23931
25
- ngpt-3.5.2.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
26
- ngpt-3.5.2.dist-info/entry_points.txt,sha256=SqAAvLhMrsEpkIr4YFRdUeyuXQ9o0IBCeYgE6AVojoI,44
27
- ngpt-3.5.2.dist-info/licenses/LICENSE,sha256=mQkpWoADxbHqE0HRefYLJdm7OpdrXBr3vNv5bZ8w72M,1065
28
- ngpt-3.5.2.dist-info/RECORD,,
24
+ ngpt-3.5.4.dist-info/METADATA,sha256=WsWK9nXRRHXbsHaeC28mdNEaw3GrSlwripN_LPJ1Mco,23912
25
+ ngpt-3.5.4.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
26
+ ngpt-3.5.4.dist-info/entry_points.txt,sha256=SqAAvLhMrsEpkIr4YFRdUeyuXQ9o0IBCeYgE6AVojoI,44
27
+ ngpt-3.5.4.dist-info/licenses/LICENSE,sha256=mQkpWoADxbHqE0HRefYLJdm7OpdrXBr3vNv5bZ8w72M,1065
28
+ ngpt-3.5.4.dist-info/RECORD,,
File without changes