Skip to content

Commit e5b0ccd

Browse files
committed
Render markdown for directories
1 parent 5e94676 commit e5b0ccd

File tree

2 files changed

+65
-0
lines changed

2 files changed

+65
-0
lines changed

runtimepy/net/server/__init__.py

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@
2424
from runtimepy.net.http.response import ResponseHeader
2525
from runtimepy.net.server.html import HtmlApp, HtmlApps, get_html, html_handler
2626
from runtimepy.net.server.json import encode_json, json_handler
27+
from runtimepy.net.server.markdown import markdown_for_dir
2728
from runtimepy.net.tcp.http import HttpConnection
2829
from runtimepy.util import normalize_root, path_has_part, read_binary
2930

@@ -189,6 +190,7 @@ async def try_file(
189190
md_candidate, response, path[1]
190191
)
191192

193+
# Handle files.
192194
if candidate.is_file():
193195
mime, encoding = mimetypes.guess_type(candidate, strict=False)
194196

@@ -203,7 +205,17 @@ async def try_file(
203205

204206
# Return the file data.
205207
result = await read_binary(candidate)
208+
break
206209

210+
# Handle directories.
211+
if candidate.is_dir():
212+
result = self.render_markdown(
213+
markdown_for_dir(
214+
candidate, {"applications": self.apps.keys()}
215+
),
216+
response,
217+
path[1],
218+
)
207219
break
208220

209221
return result

runtimepy/net/server/markdown.py

Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
"""
2+
A module implementing web server markdown interfaces.
3+
"""
4+
5+
# built-in
6+
from io import StringIO
7+
from pathlib import Path
8+
from typing import Iterable, cast
9+
10+
# third-party
11+
from vcorelib.io.file_writer import IndentedFileWriter
12+
from vcorelib.paths import rel
13+
14+
LOGO_MARKDOWN = (
15+
"[![logo](https://libre-embedded.com/static/"
16+
"png/chip-circle-bootstrap/128x128.png)](https://libre-embedded.com)"
17+
)
18+
19+
20+
def markdown_for_dir(
21+
path: Path, extra_links: dict[str, Iterable[str]] = None
22+
) -> str:
23+
"""Get markdown data for a directory."""
24+
25+
with IndentedFileWriter.string() as writer:
26+
writer.write(f"# Directory {LOGO_MARKDOWN} Viewer")
27+
with writer.padding():
28+
writer.write("---")
29+
30+
if extra_links:
31+
for category, apps in extra_links.items():
32+
writer.write(f"## {category}")
33+
with writer.padding():
34+
for app in apps:
35+
writer.write(f"* [{app}]({app})")
36+
37+
writer.write(f"## `{path}`")
38+
writer.empty()
39+
40+
writer.write("* [..](..)")
41+
42+
for item in path.iterdir():
43+
curr = rel(item, base=path)
44+
45+
name = f"`{curr}`"
46+
if item.is_dir():
47+
name = f"**{name}**"
48+
49+
writer.write(f"* [{name}]({curr})")
50+
51+
result: str = cast(StringIO, writer.stream).getvalue()
52+
53+
return result

0 commit comments

Comments
 (0)