Add simplistic autoserve/update mechanism.
This commit is contained in:
parent
a3ad99cb61
commit
7afb6be68f
111
scripts/autoserve.py
Normal file
111
scripts/autoserve.py
Normal file
@ -0,0 +1,111 @@
|
||||
#!/usr/bin/env python3
|
||||
|
||||
import sys
|
||||
import http.server
|
||||
import socketserver
|
||||
import threading
|
||||
import os
|
||||
import time
|
||||
import select
|
||||
|
||||
import inotify.adapters
|
||||
|
||||
PORT = 8000
|
||||
|
||||
MONITORED_EVENT_TYPES = (
|
||||
'IN_CREATE',
|
||||
# 'IN_MODIFY',
|
||||
'IN_CLOSE_WRITE',
|
||||
'IN_DELETE',
|
||||
'IN_MOVED_FROM',
|
||||
'IN_MOVED_TO',
|
||||
'IN_DELETE_SELF',
|
||||
'IN_MOVE_SELF',
|
||||
)
|
||||
|
||||
WAITING_RESPONSES = []
|
||||
SLEEP_TIME = 0.5
|
||||
COUNTER = 0
|
||||
MAX_WAITS = 100
|
||||
|
||||
class Server(http.server.SimpleHTTPRequestHandler):
|
||||
def do_GET(self):
|
||||
if self.path.strip('/') == '__wait_for_changes':
|
||||
WAITING_RESPONSES.append(self)
|
||||
print(len(WAITING_RESPONSES), "waiting responses")
|
||||
global COUNTER
|
||||
ticket, COUNTER = COUNTER, COUNTER + 1
|
||||
|
||||
while self in WAITING_RESPONSES:
|
||||
# This is an horribe way to wait! ... but it may work for quick tests 🤷
|
||||
|
||||
if COUNTER - ticket > MAX_WAITS:
|
||||
# Connection closed by the other side
|
||||
print("Manually closed for cleanup")
|
||||
WAITING_RESPONSES.remove(self)
|
||||
# send 502 response, timeout
|
||||
self.send_response(502)
|
||||
# send response headers
|
||||
self.end_headers()
|
||||
|
||||
return
|
||||
|
||||
time.sleep(SLEEP_TIME)
|
||||
return
|
||||
|
||||
# send 200 response
|
||||
self.send_response(200)
|
||||
# send response headers
|
||||
self.end_headers()
|
||||
|
||||
with open(self.path.strip('/'), 'rb') as f:
|
||||
# send the body of the response
|
||||
self.wfile.write(f.read())
|
||||
|
||||
if not self.path.endswith('.html'):
|
||||
return
|
||||
else:
|
||||
# Append update waiter
|
||||
with open('wait_for_update.js', 'rb') as f:
|
||||
new_data = b'<script>' + f.read() + b'</script>'
|
||||
self.wfile.write(new_data)
|
||||
new_data_len = len(new_data)
|
||||
|
||||
return
|
||||
|
||||
def notify_reloads():
|
||||
while len(WAITING_RESPONSES) > 0:
|
||||
# Close opened connections
|
||||
res = WAITING_RESPONSES.pop(0)
|
||||
|
||||
try:
|
||||
# send 200 response
|
||||
res.send_response(200)
|
||||
# send response headers
|
||||
res.end_headers()
|
||||
except Exception as e:
|
||||
print("ERROR:", e)
|
||||
|
||||
global COUNTER
|
||||
COUNTER = 0
|
||||
|
||||
|
||||
def start_notifier():
|
||||
notifier = inotify.adapters.InotifyTree(os.getcwd())
|
||||
for event in notifier.event_gen(yield_nones=False):
|
||||
(ev, types, directory, file) = event
|
||||
if any([type in MONITORED_EVENT_TYPES for type in types]):
|
||||
notify_reloads()
|
||||
|
||||
def serve():
|
||||
Handler = Server
|
||||
notifier_thread = threading.Thread(target=start_notifier)
|
||||
|
||||
with http.server.ThreadingHTTPServer(("127.0.0.1", PORT), Handler) as httpd:
|
||||
print("serving at port", PORT)
|
||||
notifier_thread.start()
|
||||
httpd.serve_forever()
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
serve()
|
19
wait_for_update.js
Normal file
19
wait_for_update.js
Normal file
@ -0,0 +1,19 @@
|
||||
(function (){
|
||||
var wait_for_update = function() {
|
||||
console.debug("Waiting for changes...");
|
||||
|
||||
fetch('/__wait_for_changes').then(r => {
|
||||
if (r.status !== 200) {
|
||||
setTimeout(
|
||||
wait_for_update,
|
||||
1000,
|
||||
);
|
||||
}
|
||||
else {
|
||||
// Reload
|
||||
window.location = window.location;
|
||||
}
|
||||
});
|
||||
};
|
||||
wait_for_update();
|
||||
})();
|
Loading…
Reference in New Issue
Block a user