pywebexec 1.2.6__py3-none-any.whl → 1.2.8__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 +1 -0
- pywebexec/static/css/style.css +82 -5
- pywebexec/static/images/down-arrow.svg +1 -0
- pywebexec/static/js/commands.js +205 -0
- pywebexec/static/js/script.js +26 -31
- pywebexec/templates/index.html +10 -4
- pywebexec/version.py +2 -2
- {pywebexec-1.2.6.dist-info → pywebexec-1.2.8.dist-info}/METADATA +2 -2
- {pywebexec-1.2.6.dist-info → pywebexec-1.2.8.dist-info}/RECORD +13 -11
- {pywebexec-1.2.6.dist-info → pywebexec-1.2.8.dist-info}/LICENSE +0 -0
- {pywebexec-1.2.6.dist-info → pywebexec-1.2.8.dist-info}/WHEEL +0 -0
- {pywebexec-1.2.6.dist-info → pywebexec-1.2.8.dist-info}/entry_points.txt +0 -0
- {pywebexec-1.2.6.dist-info → pywebexec-1.2.8.dist-info}/top_level.txt +0 -0
pywebexec/pywebexec.py
CHANGED
@@ -580,6 +580,7 @@ def get_command_output(command_id):
|
|
580
580
|
@app.route('/executables', methods=['GET'])
|
581
581
|
def list_executables():
|
582
582
|
executables = [f for f in os.listdir('.') if os.path.isfile(f) and os.access(f, os.X_OK)]
|
583
|
+
executables.sort() # Sort the list of executables alphabetically
|
583
584
|
return jsonify(executables)
|
584
585
|
|
585
586
|
def main():
|
pywebexec/static/css/style.css
CHANGED
@@ -34,6 +34,8 @@ select { /* Safari bug */
|
|
34
34
|
font-size: 15px;
|
35
35
|
border: #aaa solid 1px;
|
36
36
|
border-radius: 5px;
|
37
|
+
padding: 0px 5px 5px 0px;
|
38
|
+
min-width: 150px;
|
37
39
|
}
|
38
40
|
.output {
|
39
41
|
white-space: pre-wrap;
|
@@ -62,6 +64,11 @@ button {
|
|
62
64
|
form {
|
63
65
|
padding-bottom: 15px;
|
64
66
|
}
|
67
|
+
.form-inline {
|
68
|
+
display: flex;
|
69
|
+
align-items: center;
|
70
|
+
gap: 10px;
|
71
|
+
}
|
65
72
|
.status-icon {
|
66
73
|
display: inline-block;
|
67
74
|
width: 16px;
|
@@ -103,21 +110,89 @@ form {
|
|
103
110
|
.copy_clip_ok, .copy_clip_ok:hover {
|
104
111
|
background-image: url("/static/images/copy_ok.svg");
|
105
112
|
}
|
106
|
-
|
107
|
-
width: 50%;
|
113
|
+
#params, #commandName {
|
108
114
|
-webkit-appearance: none;
|
109
115
|
-webkit-border-radius: none;
|
110
116
|
appearance: none;
|
111
117
|
border-radius: 15px;
|
112
118
|
padding: 3px;
|
113
|
-
padding-right: 13px;
|
114
119
|
border: 1px #aaa solid;
|
115
120
|
height: 15px;
|
116
121
|
font-size: 15px;
|
117
122
|
outline: none;
|
123
|
+
background-color: white;
|
124
|
+
margin: 0; /* Remove margin */
|
125
|
+
}
|
126
|
+
|
127
|
+
#commandName {
|
128
|
+
width: auto; /* Allow dynamic width */
|
129
|
+
background-size: 16px 16px;
|
130
|
+
border-radius: 15px 0px 0px 15px;
|
131
|
+
border-right: 0px;
|
118
132
|
text-indent: 5px;
|
133
|
+
padding-right: 0px;
|
134
|
+
}
|
135
|
+
#params {
|
136
|
+
width: auto; /* Allow dynamic width */
|
137
|
+
border-radius: 0px 15px 15px 0px;
|
138
|
+
border-left: 0px;
|
139
|
+
}
|
140
|
+
|
141
|
+
.input-group {
|
142
|
+
display: flex;
|
143
|
+
align-items: center;
|
144
|
+
/*width: 60%;*/
|
145
|
+
}
|
146
|
+
|
147
|
+
.show-command-list-button {
|
119
148
|
background-color: white;
|
149
|
+
cursor: pointer;
|
150
|
+
height: 21px;
|
151
|
+
font-size: 15px;
|
152
|
+
border-top: 1px solid #aaa;
|
153
|
+
border-bottom: 1px solid #aaa;
|
154
|
+
border-radius: 0px;
|
155
|
+
display: flex;
|
156
|
+
align-items: center;
|
157
|
+
justify-content: center;
|
158
|
+
}
|
159
|
+
|
160
|
+
.show-command-list-button .arrow {
|
161
|
+
visibility: hidden; /* Hide arrow by default */
|
162
|
+
}
|
163
|
+
|
164
|
+
.show-command-list-button:hover .arrow {
|
165
|
+
visibility: visible; /* Show arrow on hover */
|
166
|
+
}
|
167
|
+
|
168
|
+
#commandName:focus + .show-command-list-button .arrow {
|
169
|
+
visibility: visible; /* Show arrow when input has focus */
|
170
|
+
}
|
171
|
+
|
172
|
+
#commandList.show + .show-command-list-button .arrow {
|
173
|
+
display: none; /* Hide arrow when list is shown */
|
174
|
+
}
|
175
|
+
|
176
|
+
.command-list {
|
177
|
+
display: none;
|
178
|
+
position: absolute;
|
179
|
+
background-color: white;
|
180
|
+
border: 1px solid #aaa;
|
181
|
+
border-radius: 5px;
|
182
|
+
padding: 0px 5px 0px 5px;
|
183
|
+
overflow-y: auto;
|
184
|
+
z-index: 1000;
|
185
|
+
}
|
186
|
+
|
187
|
+
.command-item {
|
188
|
+
padding: 3px 5px 3px 5px;
|
189
|
+
cursor: pointer;
|
190
|
+
}
|
191
|
+
|
192
|
+
.command-item:hover, .command-item.highlighted {
|
193
|
+
background-color: #eee;
|
120
194
|
}
|
195
|
+
|
121
196
|
.currentcommand {
|
122
197
|
background-color: #eef;
|
123
198
|
}
|
@@ -172,6 +247,8 @@ body.dimmed * {
|
|
172
247
|
visibility: hidden;
|
173
248
|
height: 0px;
|
174
249
|
}
|
175
|
-
|
176
|
-
|
250
|
+
/* allow wide chars in terminal */
|
251
|
+
span {
|
252
|
+
letter-spacing: -0.03px !important;
|
177
253
|
}
|
254
|
+
|
@@ -0,0 +1 @@
|
|
1
|
+
<svg width="12" height="12" xmlns="http://www.w3.org/2000/svg"><polygon points="4 3 12 3 8 10 4 3" fill="black" /></svg>
|
@@ -0,0 +1,205 @@
|
|
1
|
+
// commands.js
|
2
|
+
let commandInput = document.getElementById('commandName');
|
3
|
+
let paramsInput = document.getElementById('params');
|
4
|
+
let commandListSelect = document.getElementById('commandList');
|
5
|
+
let showCommandListButton = document.getElementById('showCommandListButton');
|
6
|
+
let isHandlingKeydown = false;
|
7
|
+
|
8
|
+
function unfilterCommands() {
|
9
|
+
const options = commandListSelect.options;
|
10
|
+
for (let i = 0; i < options.length; i++) {
|
11
|
+
options[i].style.display = 'block';
|
12
|
+
}
|
13
|
+
commandListSelect.size = Math.min(20, commandListSelect.options.length);
|
14
|
+
}
|
15
|
+
|
16
|
+
function filterCommands() {
|
17
|
+
const value = commandInput.value.slice(0, commandInput.selectionStart);
|
18
|
+
const options = commandListSelect.options;
|
19
|
+
let nbVisibleItems = 0;
|
20
|
+
for (let i = 0; i < options.length; i++) {
|
21
|
+
if (options[i].text.startsWith(value)) {
|
22
|
+
options[i].style.display = 'block';
|
23
|
+
nbVisibleItems += 1;
|
24
|
+
} else {
|
25
|
+
options[i].style.display = 'none';
|
26
|
+
}
|
27
|
+
}
|
28
|
+
if (nbVisibleItems>1) {
|
29
|
+
commandListSelect.size = Math.min(20, nbVisibleItems);
|
30
|
+
} else {
|
31
|
+
commandListSelect.style.display = 'none';
|
32
|
+
}
|
33
|
+
}
|
34
|
+
|
35
|
+
function setCommandListPosition() {
|
36
|
+
const rect = commandInput.getBoundingClientRect();
|
37
|
+
commandListSelect.style.left = `${rect.left}px`;
|
38
|
+
commandListSelect.style.top = `${rect.bottom}px`;
|
39
|
+
}
|
40
|
+
|
41
|
+
function adjustInputWidth(input) {
|
42
|
+
input.style.width = 'auto';
|
43
|
+
input.style.width = `${input.scrollWidth}px`;
|
44
|
+
}
|
45
|
+
|
46
|
+
|
47
|
+
paramsInput.addEventListener('input', () => adjustInputWidth(paramsInput));
|
48
|
+
commandInput.addEventListener('input', () => {
|
49
|
+
adjustInputWidth(commandInput);
|
50
|
+
filterCommands(); // Filter commands on input
|
51
|
+
});
|
52
|
+
|
53
|
+
paramsInput.addEventListener('mouseover', () => {
|
54
|
+
paramsInput.focus();
|
55
|
+
paramsInput.setSelectionRange(0, paramsInput.value.length);
|
56
|
+
});
|
57
|
+
|
58
|
+
commandInput.addEventListener('mouseover', () => {
|
59
|
+
commandInput.focus();
|
60
|
+
commandInput.setSelectionRange(0, commandInput.value.length);
|
61
|
+
});
|
62
|
+
|
63
|
+
commandInput.addEventListener('input', (event) => {
|
64
|
+
if (event.inputType === 'deleteContentBackward') {
|
65
|
+
const newValue = commandInput.value.slice(0, -1);
|
66
|
+
commandInput.value = newValue;
|
67
|
+
commandInput.setSelectionRange(newValue.length, newValue.length);
|
68
|
+
}
|
69
|
+
const value = commandInput.value;
|
70
|
+
const options = commandListSelect.options;
|
71
|
+
if (value) {
|
72
|
+
const match = Array.from(options).find(option => option.text.startsWith(value));
|
73
|
+
if (match) {
|
74
|
+
commandInput.value = match.text;
|
75
|
+
commandInput.setSelectionRange(value.length, match.text.length);
|
76
|
+
} else {
|
77
|
+
commandInput.value = value.slice(0, -1);
|
78
|
+
}
|
79
|
+
}
|
80
|
+
filterCommands();
|
81
|
+
adjustInputWidth(commandInput); // Adjust width on input
|
82
|
+
});
|
83
|
+
|
84
|
+
commandInput.addEventListener('keydown', (event) => {
|
85
|
+
if (event.key === ' ' || event.key === 'ArrowRight') {
|
86
|
+
event.preventDefault();
|
87
|
+
paramsInput.focus();
|
88
|
+
paramsInput.setSelectionRange(0, paramsInput.value.length);
|
89
|
+
} else if (event.key === 'ArrowDown') {
|
90
|
+
/*setCommandListPosition();*/
|
91
|
+
unfilterCommands();
|
92
|
+
commandListSelect.style.display = 'block';
|
93
|
+
commandListSelect.focus();
|
94
|
+
commandListSelect.selectedIndex = 0;
|
95
|
+
event.preventDefault();
|
96
|
+
}
|
97
|
+
});
|
98
|
+
|
99
|
+
paramsInput.addEventListener('keydown', (event) => {
|
100
|
+
if (event.key === 'ArrowLeft' && paramsInput.selectionStart === 0) {
|
101
|
+
commandInput.focus();
|
102
|
+
commandInput.setSelectionRange(0, commandInput.value.length);
|
103
|
+
event.preventDefault();
|
104
|
+
}
|
105
|
+
});
|
106
|
+
|
107
|
+
commandListSelect.addEventListener('keydown', (event) => {
|
108
|
+
if (event.key === 'Enter') {
|
109
|
+
event.preventDefault(); // Prevent form submission
|
110
|
+
const selectedOption = commandListSelect.options[commandListSelect.selectedIndex];
|
111
|
+
commandInput.value = selectedOption.text;
|
112
|
+
commandListSelect.style.display = 'none';
|
113
|
+
adjustInputWidth(commandInput);
|
114
|
+
paramsInput.focus();
|
115
|
+
return;
|
116
|
+
}
|
117
|
+
if (event.key === 'ArrowUp' && commandListSelect.selectedIndex == 0) {
|
118
|
+
commandInput.focus();
|
119
|
+
commandListSelect.style.display = 'none'
|
120
|
+
}
|
121
|
+
});
|
122
|
+
|
123
|
+
commandListSelect.addEventListener('click', (event) => {
|
124
|
+
event.preventDefault(); // Prevent form submission
|
125
|
+
const selectedOption = commandListSelect.options[commandListSelect.selectedIndex];
|
126
|
+
commandInput.value = selectedOption.text;
|
127
|
+
commandListSelect.style.display = 'none';
|
128
|
+
adjustInputWidth(commandInput);
|
129
|
+
paramsInput.focus();
|
130
|
+
});
|
131
|
+
|
132
|
+
|
133
|
+
commandInput.addEventListener('click', () => {
|
134
|
+
setCommandListPosition();
|
135
|
+
if (commandListSelect.style.display == 'none')
|
136
|
+
commandListSelect.style.display = 'block';
|
137
|
+
else
|
138
|
+
commandListSelect.style.display = 'none';
|
139
|
+
filterCommands();
|
140
|
+
});
|
141
|
+
|
142
|
+
commandInput.addEventListener('blur', (event) => {
|
143
|
+
if (event.relatedTarget === showCommandListButton || event.relatedTarget === commandListSelect) {
|
144
|
+
event.preventDefault();
|
145
|
+
return;
|
146
|
+
}
|
147
|
+
commandListSelect.style.display = 'none';
|
148
|
+
adjustInputWidth(commandInput);
|
149
|
+
});
|
150
|
+
|
151
|
+
showCommandListButton.addEventListener('click', (event) => {
|
152
|
+
event.preventDefault();
|
153
|
+
setCommandListPosition();
|
154
|
+
if (commandListSelect.style.display == 'none')
|
155
|
+
commandListSelect.style.display = 'block';
|
156
|
+
else
|
157
|
+
commandListSelect.style.display = 'none';
|
158
|
+
unfilterCommands();
|
159
|
+
});
|
160
|
+
|
161
|
+
window.addEventListener('click', (event) => {
|
162
|
+
if (!commandInput.contains(event.target) && !commandListSelect.contains(event.target) && !showCommandListButton.contains(event.target)) {
|
163
|
+
commandListSelect.style.display = 'none';
|
164
|
+
}
|
165
|
+
});
|
166
|
+
|
167
|
+
window.addEventListener('keydown', (event) => {
|
168
|
+
if ([commandInput, paramsInput, commandListSelect].includes(document.activeElement)) return;
|
169
|
+
if (event.code === `Key${event.key.toUpperCase()}`) {
|
170
|
+
commandInput.focus();
|
171
|
+
commandInput.dispatchEvent(new KeyboardEvent('keydown', event));
|
172
|
+
}
|
173
|
+
});
|
174
|
+
|
175
|
+
window.addEventListener('resize', () => {
|
176
|
+
setCommandListPosition();
|
177
|
+
});
|
178
|
+
|
179
|
+
window.addEventListener('load', () => {
|
180
|
+
fetchExecutables();
|
181
|
+
adjustInputWidth(paramsInput); // Adjust width on load
|
182
|
+
adjustInputWidth(commandInput); // Adjust width on load
|
183
|
+
setCommandListPosition();
|
184
|
+
});
|
185
|
+
|
186
|
+
async function fetchExecutables() {
|
187
|
+
try {
|
188
|
+
const response = await fetch('/executables');
|
189
|
+
if (!response.ok) {
|
190
|
+
throw new Error('Failed to fetch command status');
|
191
|
+
}
|
192
|
+
const executables = await response.json();
|
193
|
+
commandListSelect.innerHTML = '';
|
194
|
+
executables.forEach(executable => {
|
195
|
+
const option = document.createElement('option');
|
196
|
+
option.className = 'command-item';
|
197
|
+
option.text = executable;
|
198
|
+
commandListSelect.appendChild(option);
|
199
|
+
});
|
200
|
+
} catch (error) {
|
201
|
+
alert("Failed to fetch executables");
|
202
|
+
}
|
203
|
+
commandListSelect.size = Math.min(20, commandListSelect.options.length)
|
204
|
+
|
205
|
+
}
|
pywebexec/static/js/script.js
CHANGED
@@ -7,7 +7,21 @@ const terminal = new Terminal({
|
|
7
7
|
cursorHidden: true,
|
8
8
|
disableStdin: true,
|
9
9
|
convertEol: true,
|
10
|
-
fontFamily: 'Consolas NF, monospace, courier-new, courier'
|
10
|
+
fontFamily: 'Consolas NF, monospace, courier-new, courier',
|
11
|
+
scrollBack: 999999,
|
12
|
+
theme: {
|
13
|
+
background: '#111412',
|
14
|
+
black: '#111412',
|
15
|
+
green: '#088a5b',
|
16
|
+
blue: "#2760aa",
|
17
|
+
red: '#ba1611',
|
18
|
+
yellow: "#cf8700",
|
19
|
+
magenta: "#4c3d80",
|
20
|
+
cyan: "#00a7aa",
|
21
|
+
brightBlack: "#243C4F",
|
22
|
+
brightBlue: "#5584b1",
|
23
|
+
},
|
24
|
+
rescaleOverlappingGlyphs: true,
|
11
25
|
});
|
12
26
|
const fitAddon = new FitAddon.FitAddon();
|
13
27
|
terminal.loadAddon(fitAddon);
|
@@ -42,6 +56,8 @@ document.getElementById('launchForm').addEventListener('submit', async (event) =
|
|
42
56
|
await new Promise(r => setTimeout(r, 200));
|
43
57
|
fetchCommands();
|
44
58
|
viewOutput(data.command_id);
|
59
|
+
commandInput.focus()
|
60
|
+
commandInput.setSelectionRange(0, commandInput.value.length)
|
45
61
|
} catch (error) {
|
46
62
|
console.log('Error running command:', error);
|
47
63
|
}
|
@@ -75,7 +91,7 @@ async function fetchCommands() {
|
|
75
91
|
<td>${command.command.replace(/^\.\//, '')}</td>
|
76
92
|
<td><span class="status-icon status-${command.status}"></span>${command.status}${command.status === 'failed' ? ` (${command.exit_code})` : ''}</td>
|
77
93
|
<td>
|
78
|
-
${command.status === 'running' ? `<button onclick="stopCommand('${command.command_id}')">Stop</button>` : `<button onclick="relaunchCommand('${command.command_id}')">Run</button>`}
|
94
|
+
${command.status === 'running' ? `<button onclick="stopCommand('${command.command_id}', event)">Stop</button>` : `<button onclick="relaunchCommand('${command.command_id}', event)">Run</button>`}
|
79
95
|
</td>
|
80
96
|
<td class="monospace outcol">${command.last_output_line || ''}</td>
|
81
97
|
`;
|
@@ -88,27 +104,6 @@ async function fetchCommands() {
|
|
88
104
|
}
|
89
105
|
}
|
90
106
|
|
91
|
-
async function fetchExecutables() {
|
92
|
-
try {
|
93
|
-
const response = await fetch('/executables');
|
94
|
-
if (!response.ok) {
|
95
|
-
throw new Error('Failed to fetch command status');
|
96
|
-
}
|
97
|
-
const executables = await response.json();
|
98
|
-
const commandNameSelect = document.getElementById('commandName');
|
99
|
-
commandNameSelect.innerHTML = '';
|
100
|
-
executables.forEach(executable => {
|
101
|
-
const option = document.createElement('option');
|
102
|
-
option.value = executable;
|
103
|
-
option.textContent = executable;
|
104
|
-
commandNameSelect.appendChild(option);
|
105
|
-
});
|
106
|
-
} catch (error) {
|
107
|
-
console.log('Error fetching executables:', error);
|
108
|
-
alert("Failed to fetch executables");
|
109
|
-
}
|
110
|
-
}
|
111
|
-
|
112
107
|
async function fetchOutput(url) {
|
113
108
|
try {
|
114
109
|
const response = await fetch(url);
|
@@ -155,7 +150,9 @@ async function viewOutput(command_id) {
|
|
155
150
|
}
|
156
151
|
}
|
157
152
|
|
158
|
-
async function relaunchCommand(command_id) {
|
153
|
+
async function relaunchCommand(command_id, event) {
|
154
|
+
event.stopPropagation();
|
155
|
+
event.stopImmediatePropagation();
|
159
156
|
try {
|
160
157
|
const response = await fetch(`/command_status/${command_id}`);
|
161
158
|
if (!response.ok) {
|
@@ -188,7 +185,9 @@ async function relaunchCommand(command_id) {
|
|
188
185
|
}
|
189
186
|
}
|
190
187
|
|
191
|
-
async function stopCommand(command_id) {
|
188
|
+
async function stopCommand(command_id, event) {
|
189
|
+
event.stopPropagation();
|
190
|
+
event.stopImmediatePropagation();
|
192
191
|
try {
|
193
192
|
const response = await fetch(`/stop_command/${command_id}`, {
|
194
193
|
method: 'POST'
|
@@ -269,11 +268,7 @@ function initResizer() {
|
|
269
268
|
}
|
270
269
|
|
271
270
|
window.addEventListener('resize', adjustOutputHeight);
|
272
|
-
window.addEventListener('load',
|
273
|
-
adjustOutputHeight();
|
274
|
-
initResizer();
|
275
|
-
});
|
271
|
+
window.addEventListener('load', initResizer);
|
276
272
|
|
277
|
-
fetchExecutables();
|
278
273
|
fetchCommands();
|
279
|
-
setInterval(fetchCommands, 5000);
|
274
|
+
setInterval(fetchCommands, 5000);
|
pywebexec/templates/index.html
CHANGED
@@ -12,11 +12,16 @@
|
|
12
12
|
<div class="dimmer-text">Server not reachable</div>
|
13
13
|
</div>
|
14
14
|
<h2><span class="status-icon title-icon"></span>{{ title }}</h2>
|
15
|
-
<form id="launchForm">
|
15
|
+
<form id="launchForm" class="form-inline">
|
16
16
|
<label for="commandName">Command</label>
|
17
|
-
<
|
18
|
-
|
19
|
-
|
17
|
+
<div class="input-group">
|
18
|
+
<input type="text" id="commandName" name="commandName" size=5 autocomplete="off" style="width: 100px;" autofocus>
|
19
|
+
<div id="showCommandListButton" class="show-command-list-button">
|
20
|
+
<span class="arrow">▼</span>
|
21
|
+
</div>
|
22
|
+
<select id="commandList" class="command-list" size="20"></select>
|
23
|
+
<input type="text" id="params" name="params" oninput="this.style.width = ((this.value.length + 1) * 8) + 'px';">
|
24
|
+
</div>
|
20
25
|
<button type="submit">Run</button>
|
21
26
|
</form>
|
22
27
|
<div class="table-container" id="tableContainer">
|
@@ -43,5 +48,6 @@
|
|
43
48
|
<script src="/static/js/xterm/xterm.js"></script>
|
44
49
|
<script src="/static/js/xterm/xterm-addon-fit.js"></script>
|
45
50
|
<script type="text/javascript" src="/static/js/script.js"></script>
|
51
|
+
<script type="text/javascript" src="/static/js/commands.js"></script>
|
46
52
|
</body>
|
47
53
|
</html>
|
pywebexec/version.py
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
Metadata-Version: 2.2
|
2
2
|
Name: pywebexec
|
3
|
-
Version: 1.2.
|
3
|
+
Version: 1.2.8
|
4
4
|
Summary: Simple Python HTTP Exec Server
|
5
5
|
Home-page: https://github.com/joknarf/pywebexec
|
6
6
|
Author: Franck Jouvanceau
|
@@ -83,7 +83,7 @@ $ pywebexec
|
|
83
83
|
```
|
84
84
|
|
85
85
|
* Launch commands with params/view live output/Status using browser
|
86
|
-

|
87
87
|
|
88
88
|
all commands output / statuses are available in the executables directory in subdirectory `.web_status`
|
89
89
|
|
@@ -1,25 +1,27 @@
|
|
1
1
|
pywebexec/__init__.py,sha256=4spIsVaF8RJt8S58AG_wWoORRNkws9Iwqprj27C3ljM,99
|
2
|
-
pywebexec/pywebexec.py,sha256=
|
3
|
-
pywebexec/version.py,sha256=
|
4
|
-
pywebexec/static/css/style.css,sha256=
|
2
|
+
pywebexec/pywebexec.py,sha256=LRKJ2KgklZsHawd97mSKodBpH5gLm3oMza30hcLcekc,22735
|
3
|
+
pywebexec/version.py,sha256=s3iHFZtIHrLA43BEwwqCJ5Ch9SA-UTWHAi57WzfyPLM,411
|
4
|
+
pywebexec/static/css/style.css,sha256=s3rpd-sbnu_T4MogbVjjT05edhmGdMtlwAMx_9n8834,5177
|
5
5
|
pywebexec/static/css/xterm.css,sha256=gy8_LGA7Q61DUf8ElwFQzHqHMBQnbbEmpgZcbdgeSHI,5383
|
6
6
|
pywebexec/static/images/aborted.svg,sha256=_mP43hU5QdRLFZIknBgjx-dIXrHgQG23-QV27ApXK2A,381
|
7
7
|
pywebexec/static/images/copy.svg,sha256=d9OwtGh5GzzZHzYcDrLfNxZYLth1Q64x7bRyYxu4Px0,622
|
8
8
|
pywebexec/static/images/copy_ok.svg,sha256=mEqUVUhSq8xaJK2msQkxRawnz_KwlCZ-tok8QS6hJ3g,451
|
9
|
+
pywebexec/static/images/down-arrow.svg,sha256=4TclEmntMvKk_F_ADXgTpGtviYo826EDmmZiGE7HQBI,121
|
9
10
|
pywebexec/static/images/failed.svg,sha256=ADZ7IKrUyOXtqpivnz3VcH0-Wru-I5MOi3OJAkI3hxk,1439
|
10
11
|
pywebexec/static/images/favicon.svg,sha256=ti80IfuDZwIvQcmJxkOeUaB1iMsiyOPmQmVO-h0y1IU,1126
|
11
12
|
pywebexec/static/images/running.gif,sha256=iYuzQGkMxrakSIwt6gPieKCImGZoSAHmU5MUNZa7cpw,25696
|
12
13
|
pywebexec/static/images/success.svg,sha256=PJDcCSTevJh7rkfSFLtc7P0pbeh8PVQBS8DaOLQemmc,489
|
13
|
-
pywebexec/static/js/
|
14
|
+
pywebexec/static/js/commands.js,sha256=XfrnyRVjfZ8eOq9XpJXNVVzuvzLHqa81Ot99DSRL_Rk,6954
|
15
|
+
pywebexec/static/js/script.js,sha256=1ypziT5pOmHj_15MUvBf0ChjzEpAQ-ji4W9nhxoI_iM,9775
|
14
16
|
pywebexec/static/js/xterm/LICENSE,sha256=EU1P4eXTull-_T9I80VuwnJXubB-zLzUl3xpEYj2T1M,1083
|
15
17
|
pywebexec/static/js/xterm/ansi_up.min.js,sha256=KNGV0vEr30hNqKQimTAvGVy-icD5A1JqMQTtvYtKR2Y,13203
|
16
18
|
pywebexec/static/js/xterm/xterm-addon-fit.js,sha256=Pprm9pZe4SadVXS5Bc8b9VnC9Ex4QlWwA0pxOH53Gck,1460
|
17
19
|
pywebexec/static/js/xterm/xterm.js,sha256=Bzka76jZwEhVt_LlS0e0qMw7ryGa1p5qfxFyeohphBo,283371
|
18
20
|
pywebexec/templates/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
|
19
|
-
pywebexec/templates/index.html,sha256=
|
20
|
-
pywebexec-1.2.
|
21
|
-
pywebexec-1.2.
|
22
|
-
pywebexec-1.2.
|
23
|
-
pywebexec-1.2.
|
24
|
-
pywebexec-1.2.
|
25
|
-
pywebexec-1.2.
|
21
|
+
pywebexec/templates/index.html,sha256=M-9JUAR5vrk-19oF8CpxkWJvyWJkZIa71AI-1jpsMWE,2116
|
22
|
+
pywebexec-1.2.8.dist-info/LICENSE,sha256=gRJf0JPT_wsZJsUGlWPTS8Vypfl9vQ1qjp6sNbKykuA,1064
|
23
|
+
pywebexec-1.2.8.dist-info/METADATA,sha256=lNTx0DEKtyTGW4huTsiNf-ZPfoer9Ieaz5uTndBglCE,6936
|
24
|
+
pywebexec-1.2.8.dist-info/WHEEL,sha256=In9FTNxeP60KnTkGw7wk6mJPYd_dQSjEZmXdBdMCI-8,91
|
25
|
+
pywebexec-1.2.8.dist-info/entry_points.txt,sha256=l52GBkPCXRkmlHfEyoVauyfBdg8o-CAtC8qQpOIjJK0,55
|
26
|
+
pywebexec-1.2.8.dist-info/top_level.txt,sha256=vHoHyzngrfGdm_nM7Xn_5iLmaCrf10XO1EhldgNLEQ8,10
|
27
|
+
pywebexec-1.2.8.dist-info/RECORD,,
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|