Spaces:
Sleeping
Sleeping
files
Browse files- Dockerfile +1 -1
- main.py +46 -61
Dockerfile
CHANGED
@@ -30,7 +30,7 @@ RUN $PUP
|
|
30 |
|
31 |
RUN pup py3.11
|
32 |
|
33 |
-
RUN pup fetch appenv fastapi uvicorn
|
34 |
|
35 |
COPY --chown=user main.py .
|
36 |
|
|
|
30 |
|
31 |
RUN pup py3.11
|
32 |
|
33 |
+
RUN pup fetch appenv fastapi uvicorn itables
|
34 |
|
35 |
COPY --chown=user main.py .
|
36 |
|
main.py
CHANGED
@@ -1,64 +1,49 @@
|
|
1 |
-
from fastapi import FastAPI,
|
|
|
2 |
from fastapi.responses import HTMLResponse
|
3 |
-
import
|
|
|
|
|
4 |
|
5 |
-
app = FastAPI()
|
6 |
-
|
7 |
-
# HTML template for the terminal interface
|
8 |
-
index_html = """
|
9 |
-
<!DOCTYPE html>
|
10 |
-
<html lang="en">
|
11 |
-
<head>
|
12 |
-
<meta charset="UTF-8">
|
13 |
-
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
14 |
-
<title>Web Terminal</title>
|
15 |
-
<style>
|
16 |
-
/* Add CSS styles to customize the appearance of the terminal */
|
17 |
-
</style>
|
18 |
-
</head>
|
19 |
-
<body>
|
20 |
-
<div id="terminal"></div>
|
21 |
-
<script>
|
22 |
-
const terminal = document.getElementById("terminal");
|
23 |
-
const ws = new WebSocket("ws://" + window.location.host + "/terminal");
|
24 |
-
|
25 |
-
ws.onmessage = function(event) {
|
26 |
-
terminal.innerText += event.data + "\\n";
|
27 |
-
};
|
28 |
-
|
29 |
-
function sendCommand() {
|
30 |
-
const command = prompt("Enter command:");
|
31 |
-
ws.send(command);
|
32 |
-
}
|
33 |
-
</script>
|
34 |
-
</body>
|
35 |
-
</html>
|
36 |
-
"""
|
37 |
|
38 |
-
|
39 |
-
|
40 |
-
|
41 |
-
|
42 |
-
|
43 |
-
|
44 |
-
|
45 |
-
|
46 |
-
|
47 |
-
|
48 |
-
|
49 |
-
|
50 |
-
|
51 |
-
|
52 |
-
|
53 |
-
|
54 |
-
|
55 |
-
|
56 |
-
|
57 |
-
|
58 |
-
|
59 |
-
|
60 |
-
|
61 |
-
|
62 |
-
|
63 |
-
|
64 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
1 |
+
from fastapi import FastAPI, Request
|
2 |
+
from fastapi.staticfiles import StaticFiles
|
3 |
from fastapi.responses import HTMLResponse
|
4 |
+
from itables import to_html_datatable
|
5 |
+
from pathlib import Path
|
6 |
+
import pandas as pd
|
7 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
8 |
|
9 |
+
ROOT = Path(".")
|
10 |
+
app = FastAPI()
|
11 |
+
app.mount(path="/", app=StaticFiles(directory=ROOT), name="HOME")
|
12 |
+
|
13 |
+
|
14 |
+
@app.middleware("http")
|
15 |
+
async def file_system(request: Request, call_next):
|
16 |
+
url = request.url
|
17 |
+
if url.path.endswith("/"):
|
18 |
+
return HTMLResponse(content=files_in_folder(url.path.lstrip("/")))
|
19 |
+
response = await call_next(request)
|
20 |
+
return response
|
21 |
+
|
22 |
+
|
23 |
+
def files_in_folder(path: str):
|
24 |
+
"""List files to render as file index."""
|
25 |
+
folder = ROOT / path
|
26 |
+
print(folder)
|
27 |
+
path_glob = folder.glob("*")
|
28 |
+
res = pd.DataFrame(
|
29 |
+
[
|
30 |
+
(
|
31 |
+
f.name,
|
32 |
+
f.stat().st_size,
|
33 |
+
pd.Timestamp(int(f.stat().st_mtime), unit="s"),
|
34 |
+
f.stat().st_nlink > 1,
|
35 |
+
)
|
36 |
+
for f in path_glob
|
37 |
+
],
|
38 |
+
columns=["path", "size", "mtime", "folder"],
|
39 |
+
).sort_values(["folder"], ascending=False)
|
40 |
+
|
41 |
+
res["path"] = res.apply(
|
42 |
+
lambda x: f"<a href=/{path}{x.path}{'/' if x.folder else ''}>{x.path}</a>",
|
43 |
+
axis=1,
|
44 |
+
)
|
45 |
+
return f"<h1>{folder}</h1><br>" + to_html_datatable(
|
46 |
+
df=res.drop(columns="folder"),
|
47 |
+
classes="display compact",
|
48 |
+
showIndex=False,
|
49 |
+
)
|