pywebexec 1.7.6__py3-none-any.whl → 1.7.9__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.
pywebexec/pywebexec.py CHANGED
@@ -492,33 +492,31 @@ def script(output_file):
492
492
  p.interact()
493
493
 
494
494
 
495
- def run_command(fromip, user, command, params, command_id):
495
+ def run_command(fromip, user, command, params, command_id, rows, cols):
496
496
  # app.logger.info(f'{fromip} run_command {command_id} {user}: {command} {params}')
497
497
  log_info(fromip, user, f'run_command {command_id}: {command_str(command, params)}')
498
- start_time = datetime.now().isoformat()
498
+ start_time = datetime.now(timezone.utc).isoformat()
499
499
  update_command_status(command_id, {
500
500
  'status': 'running',
501
501
  'command': command,
502
502
  'params': params,
503
503
  'start_time': start_time,
504
504
  'user': user,
505
- 'cols': tty_cols,
506
- 'rows': tty_rows,
505
+ 'cols': cols,
506
+ 'rows': rows,
507
507
  })
508
508
  output_file_path = get_output_file_path(command_id)
509
509
  try:
510
510
  with open(output_file_path, 'wb') as fd:
511
- p = pexpect.spawn(command, params, ignore_sighup=True, timeout=None, dimensions=(tty_rows, tty_cols))
511
+ p = pexpect.spawn(command, params, ignore_sighup=True, timeout=None, dimensions=(rows, cols))
512
512
  update_command_status(command_id, {
513
- 'status': 'running',
514
513
  'pid': p.pid,
515
- 'user': user
516
514
  })
517
515
  p.logfile = fd
518
516
  p.expect(pexpect.EOF)
519
517
  fd.flush()
520
518
  status = p.wait()
521
- end_time = datetime.now().isoformat()
519
+ end_time = datetime.now(timezone.utc).isoformat()
522
520
  # Update the status based on the result
523
521
  if status is None:
524
522
  exit_code = -15
@@ -549,7 +547,7 @@ def run_command(fromip, user, command, params, command_id):
549
547
  log_info(fromip, user, f'run_command {command_id}: {command_str(command, params)}: exit code {exit_code}')
550
548
 
551
549
  except Exception as e:
552
- end_time = datetime.now().isoformat()
550
+ end_time = datetime.now(timezone.utc).isoformat()
553
551
  update_command_status(command_id, {
554
552
  'status': 'failed',
555
553
  'end_time': end_time,
@@ -617,7 +615,7 @@ def check_processes():
617
615
  status = read_command_status(command_id)
618
616
  if status.get('status') == 'running' and 'pid' in status:
619
617
  if not is_process_alive(status['pid']):
620
- end_time = datetime.now().isoformat()
618
+ end_time = datetime.now(timezone.utc).isoformat()
621
619
  update_command_status(command_id, {
622
620
  'status': 'aborted',
623
621
  'end_time': end_time,
@@ -643,7 +641,7 @@ def stop_command(command_id):
643
641
  return jsonify({'error': 'Invalid command_id or command not running'}), 400
644
642
 
645
643
  pid = status['pid']
646
- end_time = datetime.now().isoformat()
644
+ end_time = datetime.now(timezone.utc).isoformat()
647
645
  try:
648
646
  #update_command_status(command_id, 'aborted', end_time=end_time, exit_code=-15)
649
647
  os.killpg(os.getpgid(pid), 15) # Send SIGTERM to the process group
@@ -725,6 +723,8 @@ def run_command_endpoint():
725
723
  data = request.json
726
724
  command = data.get('command')
727
725
  params = data.get('params', [])
726
+ rows = data.get('rows', tty_rows)
727
+ cols = data.get('cols', tty_cols)
728
728
 
729
729
  if not command:
730
730
  return jsonify({'error': 'command is required'}), 400
@@ -753,7 +753,7 @@ def run_command_endpoint():
753
753
  })
754
754
 
755
755
  # Run the command in a separate thread
756
- thread = threading.Thread(target=run_command, args=(request.remote_addr, user, command_path, params, command_id))
756
+ thread = threading.Thread(target=run_command, args=(request.remote_addr, user, command_path, params, command_id, rows, cols))
757
757
  thread.start()
758
758
 
759
759
  return jsonify({'message': 'Command is running', 'command_id': command_id})
@@ -248,6 +248,7 @@ function toggleFit() {
248
248
  toggleFitButton.setAttribute('title', 'terminal fit window');
249
249
  }
250
250
  autoFit();
251
+ viewOutput(currentCommandId);
251
252
  }
252
253
 
253
254
  toggleButton.addEventListener('click', toggleFetchOutput);
@@ -128,13 +128,15 @@ document.getElementById('launchForm').addEventListener('submit', async (event) =
128
128
  event.preventDefault();
129
129
  const commandName = document.getElementById('commandName').value;
130
130
  const params = document.getElementById('params').value.split(' ');
131
+ fitAddon.fit();
132
+ terminal.clear();
131
133
  try {
132
134
  const response = await fetch(`/run_command${urlToken}`, {
133
135
  method: 'POST',
134
136
  headers: {
135
137
  'Content-Type': 'application/json'
136
138
  },
137
- body: JSON.stringify({ command: commandName, params: params })
139
+ body: JSON.stringify({ command: commandName, params: params, rows: terminal.rows, cols: terminal.cols })
138
140
  });
139
141
  if (!response.ok) {
140
142
  throw new Error('Failed to launch command');
@@ -314,6 +316,8 @@ async function relaunchCommand(command_id, event) {
314
316
  alert(data.error);
315
317
  return;
316
318
  }
319
+ fitAddon.fit();
320
+ terminal.clear();
317
321
  const relaunchResponse = await fetch(`/run_command${urlToken}`, {
318
322
  method: 'POST',
319
323
  headers: {
@@ -321,7 +325,9 @@ async function relaunchCommand(command_id, event) {
321
325
  },
322
326
  body: JSON.stringify({
323
327
  command: data.command,
324
- params: data.params
328
+ params: data.params,
329
+ rows: terminal.rows,
330
+ cols: terminal.cols,
325
331
  })
326
332
  });
327
333
  if (!relaunchResponse.ok) {
@@ -480,6 +486,7 @@ function toggleFit() {
480
486
  toggleFitButton.setAttribute('title', 'terminal fit window');
481
487
  }
482
488
  autoFit();
489
+ viewOutput(currentCommandId);
483
490
  }
484
491
 
485
492
  toggleButton.addEventListener('click', toggleFetchOutput);
pywebexec/version.py CHANGED
@@ -12,5 +12,5 @@ __version__: str
12
12
  __version_tuple__: VERSION_TUPLE
13
13
  version_tuple: VERSION_TUPLE
14
14
 
15
- __version__ = version = '1.7.6'
16
- __version_tuple__ = version_tuple = (1, 7, 6)
15
+ __version__ = version = '1.7.9'
16
+ __version_tuple__ = version_tuple = (1, 7, 9)
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.2
2
2
  Name: pywebexec
3
- Version: 1.7.6
3
+ Version: 1.7.9
4
4
  Summary: Simple Python HTTP Exec Server
5
5
  Home-page: https://github.com/joknarf/pywebexec
6
6
  Author: Franck Jouvanceau
@@ -199,7 +199,7 @@ $ curl http://myhost:8080/command_output/<command_id> -H "Accept: text/plain"
199
199
 
200
200
  | method | route | params/payload | returns
201
201
  |-----------|-----------------------------|--------------------|---------------------|
202
- | POST | /run_command | command: str<br>params: array[str] | command_id: uuid<br>message: str |
202
+ | POST | /run_command | command: str<br>params: array[str]<br>rows: int<br>cols: int | command_id: uuid<br>message: str |
203
203
  | POST | /stop_command/command_id | | message: str |
204
204
  | GET | /command_status/command_id | | command_id: uuid<br>command: str<br>params: array[str]<br>start_time: isotime<br>end_time: isotime<br>status: str<br>exit_code: int<br>last_output_line: str |
205
205
  | GET | /commands | | array of<br>command_id: uuid<br>command: str<br>start_time: isotime<br>end_time: isotime<br>status: str<br>exit_code: int<br>last_output_line: str |
@@ -1,6 +1,6 @@
1
1
  pywebexec/__init__.py,sha256=4spIsVaF8RJt8S58AG_wWoORRNkws9Iwqprj27C3ljM,99
2
- pywebexec/pywebexec.py,sha256=VBR6KmRiHNCd0ZvGEu_5sTqzVrUEPBhM8Hi6knS1QcA,33526
3
- pywebexec/version.py,sha256=MBf1E8pj__B1I7taPBbzX7t8--SrOKz18oUxfeUZC7U,411
2
+ pywebexec/pywebexec.py,sha256=MmpHK2SscvIPj1gmV9AcJXYfeaL-at5BDgLhKIxzZBc,33604
3
+ pywebexec/version.py,sha256=ODwgXLJxyAG069GuB0hTip534M1pf6WoBdbcnmuVFy0,411
4
4
  pywebexec/static/css/Consolas NF.ttf,sha256=DJEOzF0eqZ-kxu3Gs_VE8X0NJqiobBzmxWDGpdgGRxI,1313900
5
5
  pywebexec/static/css/style.css,sha256=3s7QgbCh4wb7kfZ7Pjo-B6o3lDIBogZ-3j6AfaPdpzU,8209
6
6
  pywebexec/static/css/xterm.css,sha256=uo5phWaUiJgcz0DAzv46uoByLLbJLeetYosL1xf68rY,5559
@@ -21,8 +21,8 @@ pywebexec/static/images/resume.svg,sha256=99LP1Ya2JXakRCO9kW8JMuT_4a_CannF65Eiuw
21
21
  pywebexec/static/images/running.svg,sha256=fBCYwYb2O9K4N3waC2nURP25NRwZlqR4PbDZy6JQMww,610
22
22
  pywebexec/static/images/success.svg,sha256=NVwezvVMplt46ElW798vqGfrL21Mw_DWHUp_qiD_FU8,489
23
23
  pywebexec/static/js/commands.js,sha256=h2fkd9qpypLBxvhEEbay23nwuqUwcKJA0vHugcyL8pU,7961
24
- pywebexec/static/js/popup.js,sha256=MFGDVjTrddLeeAWmUarWSSP1LiQBOJGPNaSGLn994V4,9418
25
- pywebexec/static/js/script.js,sha256=s9tL8CUXCPjCGmmug0g5E2h_J5kYuTP1eok1EYt7Q98,18287
24
+ pywebexec/static/js/popup.js,sha256=_2GzUizJ-sdZFWG7SZwbYJTPbu4EvVq7D5Q_UE8nepA,9452
25
+ pywebexec/static/js/script.js,sha256=m4qjZt0voE-FObq3GRvlYgQWSx9ApInJRtgtf3uCGqE,18530
26
26
  pywebexec/static/js/xterm/LICENSE,sha256=EU1P4eXTull-_T9I80VuwnJXubB-zLzUl3xpEYj2T1M,1083
27
27
  pywebexec/static/js/xterm/addon-canvas.js,sha256=ez6QTVvsmLVNJmdJlM-ZQ5bErwlxAQ_9DUmDIptl2TM,94607
28
28
  pywebexec/static/js/xterm/addon-canvas.js.map,sha256=ECBA4B-BqUpdFeRzlsEWLSQnudnhLP-yPQJ8_hKquMo,379537
@@ -35,9 +35,9 @@ pywebexec/static/js/xterm/xterm.js.map,sha256=Y7O2Pb-fIS7Z8AC1D5s04_aiW_Jf1f4mCf
35
35
  pywebexec/templates/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
36
36
  pywebexec/templates/index.html,sha256=CcLN3v_42lnj4juiTntDTiGHJ8-zQnmB9oqpSK_0kks,2981
37
37
  pywebexec/templates/popup.html,sha256=f5m4u8WKpkevL2mQamGqo4_y-rSuLOXGuNsezuUbniY,1508
38
- pywebexec-1.7.6.dist-info/LICENSE,sha256=gRJf0JPT_wsZJsUGlWPTS8Vypfl9vQ1qjp6sNbKykuA,1064
39
- pywebexec-1.7.6.dist-info/METADATA,sha256=7CbhFG_ZD1Jkd5D0oibOtzlTZHoQIdxN1CkeUUpCI7g,8122
40
- pywebexec-1.7.6.dist-info/WHEEL,sha256=In9FTNxeP60KnTkGw7wk6mJPYd_dQSjEZmXdBdMCI-8,91
41
- pywebexec-1.7.6.dist-info/entry_points.txt,sha256=l52GBkPCXRkmlHfEyoVauyfBdg8o-CAtC8qQpOIjJK0,55
42
- pywebexec-1.7.6.dist-info/top_level.txt,sha256=vHoHyzngrfGdm_nM7Xn_5iLmaCrf10XO1EhldgNLEQ8,10
43
- pywebexec-1.7.6.dist-info/RECORD,,
38
+ pywebexec-1.7.9.dist-info/LICENSE,sha256=gRJf0JPT_wsZJsUGlWPTS8Vypfl9vQ1qjp6sNbKykuA,1064
39
+ pywebexec-1.7.9.dist-info/METADATA,sha256=ktA3IaI3-tmiO6niFlh1iOHQTGaVLuW7T9byfexDhpM,8148
40
+ pywebexec-1.7.9.dist-info/WHEEL,sha256=In9FTNxeP60KnTkGw7wk6mJPYd_dQSjEZmXdBdMCI-8,91
41
+ pywebexec-1.7.9.dist-info/entry_points.txt,sha256=l52GBkPCXRkmlHfEyoVauyfBdg8o-CAtC8qQpOIjJK0,55
42
+ pywebexec-1.7.9.dist-info/top_level.txt,sha256=vHoHyzngrfGdm_nM7Xn_5iLmaCrf10XO1EhldgNLEQ8,10
43
+ pywebexec-1.7.9.dist-info/RECORD,,