Skip to content

Commit dd7f1d3

Browse files
committed
feat/fix: improve apidoc_ui, add tests, add auditing, performance, slugger, permissions
1 parent 7d4f639 commit dd7f1d3

File tree

18 files changed

+1834
-37
lines changed

18 files changed

+1834
-37
lines changed

Doxyfile

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,7 @@ PROJECT_NAME = "pyEchoNext"
4848
# could be handy for archiving the generated documentation or if some version
4949
# control system is used.
5050

51-
PROJECT_NUMBER = "0.5.9"
51+
PROJECT_NUMBER = "0.6.9"
5252

5353
# Using the PROJECT_BRIEF tag one can provide an optional one line description
5454
# for a project that appears at the top of each page and should give viewer a

README.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,7 @@ Welcome to **EchoNext**, where innovation meets simplicity! Are you tired of the
4242
**Imagine** a lightweight framework that empowers you to create modern web applications with lightning speed and flexibility. With EchoNext, you're not just coding; you're building a masterpiece!
4343

4444
> Last stable version: 0.5.9 alpha
45+
> Last unstable version: 0.6.9 alpha
4546
4647
> Next Big Update: ASYNC & unicorn support
4748

SECURITY.md

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,13 +7,14 @@ currently being supported with security updates.
77

88
| Version | Supported |
99
| ------- | ------------------ |
10+
| 0.6.9 | :white_check_mark: |
1011
| 0.5.9 | :white_check_mark: |
1112
| 0.5.8 | :white_check_mark: |
1213
| 0.5.7 | :white_check_mark: |
1314
| 0.5.6 | :white_check_mark: |
1415
| 0.5.5 | :white_check_mark: |
1516
| 0.5.4 | :white_check_mark: |
16-
| 0.5.3 | :white_check_mark: |
17+
| 0.5.3 | :x: |
1718
| 0.4.3 | :x: |
1819
| 0.4.2 | :x: |
1920
| 0.4.1 | :x: |

docs/ru/webapp_creation.md

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,12 @@ BASE_DIR - базовая директория файла приложения,
5252
+ ini-файл
5353
+ pymodule (модуль python)
5454

55+
А с версии 0.6.9:
56+
57+
+ toml-файл
58+
+ yaml-файл
59+
+ json-файл
60+
5561
Для его использования импортируйте:
5662

5763
```python

examples/example_locale.py

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,6 @@
77
from pyechonext.response import Response
88
from pyechonext.template_engine.jinja import render_template
99
from pyechonext.middleware import middlewares
10-
from pyechonext.docsgen import ProjDocumentation
1110
from pyechonext.apidoc_ui import APIDocumentation, APIDocUI
1211
from pyechonext.static import StaticFile
1312

@@ -39,7 +38,6 @@ def post(self, request, response, **kwargs):
3938
static_files=static_files
4039
)
4140
apidoc = APIDocumentation(echonext)
42-
projdoc = ProjDocumentation(echonext)
4341

4442

4543
@echonext.route_page('/api-docs')
@@ -49,7 +47,6 @@ def api_docs(request, response):
4947

5048

5149
@echonext.route_page("/book")
52-
@projdoc.documentate_route('/book', str, {}, ['GET', 'POST'])
5350
class BooksResource(View):
5451
"""
5552
This class describes a books resource.
@@ -86,6 +83,3 @@ def post(self, request, response, **kwargs):
8683
:rtype: str
8784
"""
8885
return echonext.l10n_loader.format_currency(1305.50)
89-
90-
91-
projdoc.generate_documentation()

examples/example_locale/docs/api/Initiation-Project_example_locale.md

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
# Initiation-Project example_locale
22
Project Documentation for example_locale
33

4-
+ *Creation date*: 2024-11-22 18:32:21
5-
+ *Modification date*: 2024-11-22 18:32:21
4+
+ *Creation date*: 2024-11-23 18:09:19
5+
+ *Modification date*: 2024-11-23 18:09:19
66

77
## Routes
88
/api-docs, /book
@@ -12,7 +12,7 @@ Project Documentation for example_locale
1212
## Subsections
1313

1414
### /book
15-
Creation date: 2024-11-22 18:32:21
15+
Creation date: 2024-11-23 18:09:19
1616

1717
#### Route
1818
Methods: ['GET', 'POST']

pyechonext/__init__.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@
2323
from rich import print
2424
from rich.traceback import install
2525

26-
__version__ = "0.5.9"
26+
__version__ = "0.6.9"
2727
install(show_locals=True)
2828

2929

pyechonext/apidoc_ui/ui.py

Lines changed: 159 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,6 @@
1+
import json
2+
3+
14
class APIDocUI:
25
"""
36
This class describes an api document ui.
@@ -19,6 +22,7 @@ def generate_section(
1922
summary_post: str,
2023
get_responses: dict,
2124
post_responses: dict,
25+
value: dict,
2226
) -> str:
2327
"""
2428
generate section
@@ -45,19 +49,21 @@ def generate_section(
4549
<span class="collapse-icon">➡️</span>
4650
</div>
4751
<div class="section-content">
52+
<pre><code class="language-json">{json.dumps(value, indent=2)}</code></pre>
4853
<div class="method">
4954
<strong>GET</strong>
50-
<p>{summary_get}</p>
55+
<p class='summary'>{summary_get}</p>
56+
5157
<div class="responses">
52-
{"".join([f"<div class='response-item'>{key}: {value["description"]}.</div>" for key, value in get_responses.items()])}
58+
{"".join([f"<div class='response-item'><span class='span-key'>{key}</span>: {value["description"]}.</div>" for key, value in get_responses.items()])}
5359
</div>
5460
</div>
5561
<div class="method">
5662
<strong>POST</strong>
57-
<p>{summary_post}</p>
63+
<p class='summary'>{summary_post}</p>
5864
<div class="responses">
5965
<div class="responses">
60-
{"".join([f"<div class='response-item'>{key}: {value["description"]}.</div>" for key, value in post_responses.items()])}
66+
{"".join([f"<div class='response-item'><span class='span-key'>{key}</span>: {value["description"]}.</div>" for key, value in post_responses.items()])}
6167
</div>
6268
</div>
6369
</div>
@@ -81,22 +87,54 @@ def generate_html_page(self) -> str:
8187
<meta charset="UTF-8">
8288
<meta name="viewport" content="width=device-width, initial-scale=1.0">
8389
<title>API Documentation</title>
90+
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.9.0/styles/default.min.css">
8491
<style>
92+
8593
body {
8694
font-family: Arial, sans-serif;
8795
margin: 0;
8896
padding: 0;
89-
background-color: #f9f9f9;
97+
background-color: #f3f3f3;
9098
color: #333;
99+
display: block;
100+
overflow-x: auto;
101+
}
102+
.span-key {
103+
font-size: 15px;
104+
color: #007bff;
91105
}
92106
h1, h2, h3 {
93107
margin: 0;
94108
padding: 10px 0;
95109
}
110+
pre {
111+
112+
margin-bottom: 10px;
113+
padding: 5px;
114+
font-family: monospace;
115+
margin: 10px;
116+
padding: 10px;
117+
white-space: pre-wrap; /* Since CSS 2.1 */
118+
white-space: -moz-pre-wrap; /* Mozilla, since 1999 */
119+
white-space: -pre-wrap; /* Opera 4-6 */
120+
white-space: -o-pre-wrap; /* Opera 7 */
121+
word-wrap: break-word; /* Internet Explorer 5.5+ */
122+
}
123+
code{
124+
border-radius: 5px;
125+
}
126+
.summary {
127+
border-radius: 4px;
128+
box-shadow: 0 2px 15px rgba(0, 0, 0, 0.1);
129+
color: #222222;
130+
padding: 10px;
131+
border-left: 2px solid #007bff;
132+
}
96133
.container {
97134
max-width: 800px;
98135
margin: 40px auto;
99136
padding: 20px;
137+
border: 1px solid #007bff3;
100138
background: #fff;
101139
border-radius: 8px;
102140
box-shadow: 0 2px 15px rgba(0, 0, 0, 0.1);
@@ -113,11 +151,10 @@ def generate_html_page(self) -> str:
113151
}
114152
.section {
115153
border-radius: 5px;
116-
overflow: hidden;
117-
margin-bottom: 20px;
118154
transition: box-shadow 0.3s ease;
119155
}
120156
.section-header {
157+
margin-bottom: 10px;
121158
padding: 15px;
122159
background: #007bff;
123160
color: white;
@@ -133,6 +170,7 @@ def generate_html_page(self) -> str:
133170
display: none;
134171
overflow: hidden;
135172
background-color: #f1f1f1;
173+
margin-bottom: 10px;
136174
}
137175
.method {
138176
border-bottom: 1px solid #ddd;
@@ -152,14 +190,103 @@ def generate_html_page(self) -> str:
152190
}
153191
.collapse-icon {
154192
transition: transform 0.3s;
155-
}
156-
.collapse-icon.collapsed {
157193
transform: rotate(90deg);
158194
}
159-
.section:hover {
160-
box-shadow: 0 4px 20px rgba(0, 0, 0, 0.15);
195+
.collapse-icon.collapsed {
196+
transform: rotate(0deg);
161197
}
198+
pre code.hljs {
199+
display: block;
200+
overflow-x: auto;
201+
padding: 1em
202+
}
203+
code.hljs {
204+
padding: 3px 5px
205+
}
206+
/*
207+
208+
Atom One Light by Daniel Gamage
209+
Original One Light Syntax theme from https://github.com/atom/one-light-syntax
210+
211+
base: #fafafa
212+
mono-1: #383a42
213+
mono-2: #686b77
214+
mono-3: #a0a1a7
215+
hue-1: #0184bb
216+
hue-2: #4078f2
217+
hue-3: #a626a4
218+
hue-4: #50a14f
219+
hue-5: #e45649
220+
hue-5-2: #c91243
221+
hue-6: #986801
222+
hue-6-2: #c18401
223+
224+
*/
225+
.hljs {
226+
color: #383a42;
227+
background: #fafafa
228+
}
229+
.hljs-comment,
230+
.hljs-quote {
231+
color: #a0a1a7;
232+
font-style: italic
233+
}
234+
.hljs-doctag,
235+
.hljs-keyword,
236+
.hljs-formula {
237+
color: #a626a4
238+
}
239+
.hljs-section,
240+
.hljs-name,
241+
.hljs-selector-tag,
242+
.hljs-deletion,
243+
.hljs-subst {
244+
color: #e45649
245+
}
246+
.hljs-literal {
247+
color: #0184bb
248+
}
249+
.hljs-string,
250+
.hljs-regexp,
251+
.hljs-addition,
252+
.hljs-attribute,
253+
.hljs-meta .hljs-string {
254+
color: #50a14f
255+
}
256+
.hljs-attr,
257+
.hljs-variable,
258+
.hljs-template-variable,
259+
.hljs-type,
260+
.hljs-selector-class,
261+
.hljs-selector-attr,
262+
.hljs-selector-pseudo,
263+
.hljs-number {
264+
color: #986801
265+
}
266+
.hljs-symbol,
267+
.hljs-bullet,
268+
.hljs-link,
269+
.hljs-meta,
270+
.hljs-selector-id,
271+
.hljs-title {
272+
color: #4078f2
273+
}
274+
.hljs-built_in,
275+
.hljs-title.class_,
276+
.hljs-class .hljs-title {
277+
color: #c18401
278+
}
279+
.hljs-emphasis {
280+
font-style: italic
281+
}
282+
.hljs-strong {
283+
font-weight: bold
284+
}
285+
.hljs-link {
286+
text-decoration: underline
287+
}
162288
</style>
289+
163290
</head>
164291
<body>
165292
@@ -176,6 +303,19 @@ def generate_html_page(self) -> str:
176303
177304
{{sections}}
178305
306+
<br>
307+
<hr>
308+
<br>
309+
310+
<h2>Full specification</h2>
311+
<pre><code class="language-json">{{spec}}</code></pre>
312+
313+
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.9.0/highlight.min.js"></script>
314+
315+
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.9.0/languages/json.min.js"></script>
316+
317+
<script>hljs.highlightAll();</script>
318+
179319
<script>
180320
document.querySelectorAll('.section-header').forEach(header => {
181321
header.addEventListener('click', () => {
@@ -191,6 +331,12 @@ def generate_html_page(self) -> str:
191331
}
192332
});
193333
});
334+
335+
document.addEventListener('DOMContentLoaded', (event) => {
336+
document.querySelectorAll('pre code').forEach((el) => {
337+
hljs.highlightElement(el);
338+
});
339+
});
194340
</script>
195341
196342
</body>
@@ -199,6 +345,7 @@ def generate_html_page(self) -> str:
199345

200346
content = {
201347
"{{openapi-version}}": self.specification["openapi"],
348+
"{{spec}}": json.dumps(self.specification, indent=2),
202349
"{{info_title}}": self.specification["info"]["title"],
203350
"{{info_version}}": self.specification["info"]["version"],
204351
"{{info_description}}": self.specification["info"]["description"],
@@ -210,6 +357,7 @@ def generate_html_page(self) -> str:
210357
value["post"]["summary"],
211358
value["get"]["responses"],
212359
value["post"]["responses"],
360+
value,
213361
)
214362
for path, value in self.specification["paths"].items()
215363
]

0 commit comments

Comments
 (0)