drf-to-mkdoc 0.1.5__py3-none-any.whl → 0.1.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.

Potentially problematic release.


This version of drf-to-mkdoc might be problematic. Click here for more details.

Files changed (42) hide show
  1. drf_to_mkdoc/__init__.py +1 -1
  2. drf_to_mkdoc/apps.py +6 -2
  3. drf_to_mkdoc/conf/defaults.py +0 -1
  4. drf_to_mkdoc/conf/settings.py +11 -5
  5. drf_to_mkdoc/management/commands/build_docs.py +61 -19
  6. drf_to_mkdoc/management/commands/generate_docs.py +5 -5
  7. drf_to_mkdoc/management/commands/generate_model_docs.py +37 -7
  8. drf_to_mkdoc/static/drf-to-mkdoc/javascripts/endpoints-filter.js +189 -0
  9. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/accessibility.css +21 -0
  10. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/animations.css +11 -0
  11. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/badges.css +54 -0
  12. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/base.css +84 -0
  13. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/endpoint-content.css +165 -0
  14. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/endpoints-grid.css +194 -0
  15. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/filter-section.css +209 -0
  16. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/fixes.css +44 -0
  17. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/layout.css +31 -0
  18. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/loading.css +35 -0
  19. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/responsive.css +96 -0
  20. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/sections.css +35 -0
  21. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/stats.css +34 -0
  22. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/tags.css +92 -0
  23. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/theme-toggle.css +42 -0
  24. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/variables.css +73 -0
  25. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/models/animations.css +25 -0
  26. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/models/base.css +83 -0
  27. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/models/model-cards.css +126 -0
  28. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/models/model-tables.css +57 -0
  29. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/models/responsive.css +51 -0
  30. drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/models/variables.css +46 -0
  31. drf_to_mkdoc/utils/common.py +31 -29
  32. drf_to_mkdoc/utils/{endpoint_generator.py → endpoint_detail_generator.py} +214 -384
  33. drf_to_mkdoc/utils/endpoint_list_generator.py +234 -0
  34. drf_to_mkdoc/utils/extractors/query_parameter_extractors.py +15 -16
  35. drf_to_mkdoc/utils/{model_generator.py → model_detail_generator.py} +20 -51
  36. drf_to_mkdoc/utils/model_list_generator.py +67 -0
  37. {drf_to_mkdoc-0.1.5.dist-info → drf_to_mkdoc-0.1.8.dist-info}/METADATA +3 -25
  38. drf_to_mkdoc-0.1.8.dist-info/RECORD +50 -0
  39. drf_to_mkdoc-0.1.5.dist-info/RECORD +0 -25
  40. {drf_to_mkdoc-0.1.5.dist-info → drf_to_mkdoc-0.1.8.dist-info}/WHEEL +0 -0
  41. {drf_to_mkdoc-0.1.5.dist-info → drf_to_mkdoc-0.1.8.dist-info}/licenses/LICENSE +0 -0
  42. {drf_to_mkdoc-0.1.5.dist-info → drf_to_mkdoc-0.1.8.dist-info}/top_level.txt +0 -0
@@ -0,0 +1,234 @@
1
+ from pathlib import Path
2
+ from typing import Any
3
+
4
+ from django.templatetags.static import static
5
+
6
+ from drf_to_mkdoc.conf.settings import drf_to_mkdoc_settings
7
+ from drf_to_mkdoc.utils.common import extract_viewset_from_operation_id
8
+
9
+
10
+ class EndpointsIndexGenerator:
11
+ def __init__(self, active_filters: list[str] | None = None):
12
+ self.active_filters = set(
13
+ active_filters
14
+ or [
15
+ "method",
16
+ "path",
17
+ "app",
18
+ "models",
19
+ "auth",
20
+ "roles",
21
+ "content_type",
22
+ "params",
23
+ "schema",
24
+ "pagination",
25
+ "ordering",
26
+ "search",
27
+ "tags",
28
+ ]
29
+ )
30
+
31
+ def create_endpoint_card(
32
+ self, endpoint: dict[str, Any], app_name: str, viewset_name: str
33
+ ) -> str:
34
+ method = endpoint["method"]
35
+ path = endpoint["path"]
36
+ filename = endpoint["filename"]
37
+ view_class = extract_viewset_from_operation_id(endpoint["operation_id"])
38
+
39
+ link_url = f"{app_name}/{viewset_name.lower()}/{filename}".replace(".md", "/index.html")
40
+ data_attrs = f"""
41
+ data-method="{method.lower()}"
42
+ data-path="{path.lower()}"
43
+ data-app="{app_name.lower()}"
44
+ data-auth="{str(endpoint.get("auth_required", False)).lower()}"
45
+ data-pagination="{str(endpoint.get("pagination_support", False)).lower()}"
46
+ data-search="{str(bool(getattr(view_class, "search_fields", []))).lower()}"
47
+ data-ordering="{str(endpoint.get("ordering_support", False)).lower()}"
48
+ data-models="{" ".join(endpoint.get("related_models", [])).lower()}"
49
+ data-roles="{" ".join(endpoint.get("permission_roles", [])).lower()}"
50
+ data-content-type="{endpoint.get("content_type", "").lower()}"
51
+ data-tags="{" ".join(endpoint.get("tags", [])).lower()}"
52
+ data-schema="{" ".join(endpoint.get("schema_fields", [])).lower()}"
53
+ data-params="{" ".join(endpoint.get("query_parameters", [])).lower()}"
54
+ """.strip()
55
+
56
+ return f"""
57
+ <a href="{link_url}" class="endpoint-card" {data_attrs}>
58
+ <span class="method-badge method-{method.lower()}">{method}</span>
59
+ <span class="endpoint-path">{path}</span>
60
+ </a>
61
+ """
62
+
63
+ def create_filter_section(self) -> str:
64
+ filter_fields = {
65
+ "method": """<div class="filter-group">
66
+ <label class="filter-label">HTTP Method</label>
67
+ <select id="filter-method" class="filter-select">
68
+ <option value="">All</option>
69
+ <option value="get">GET</option>
70
+ <option value="post">POST</option>
71
+ <option value="put">PUT</option>
72
+ <option value="patch">PATCH</option>
73
+ <option value="delete">DELETE</option>
74
+ </select>
75
+ </div>""",
76
+ "path": """<div class="filter-group">
77
+ <label class="filter-label">Endpoint Path</label>
78
+ <input type="text" id="filter-path" class="filter-input"
79
+ placeholder="Search path...">
80
+ </div>""",
81
+ "app": """<div class="filter-group">
82
+ <label class="filter-label">Django App</label>
83
+ <select id="filter-app" class="filter-select">
84
+ <option value="">All</option>
85
+ <!-- Dynamically filled -->
86
+ </select>
87
+ </div>""",
88
+ "models": """<div class="filter-group">
89
+ <label class="filter-label">Related Models</label>
90
+ <input type="text" id="filter-models" class="filter-input">
91
+ </div>""",
92
+ "auth": """<div class="filter-group">
93
+ <label class="filter-label">Authentication Required</label>
94
+ <select id="filter-auth" class="filter-select">
95
+ <option value="">All</option>
96
+ <option value="true">Yes</option>
97
+ <option value="false">No</option>
98
+ </select>
99
+ </div>""",
100
+ "roles": """<div class="filter-group">
101
+ <label class="filter-label">Permission Roles</label>
102
+ <input type="text" id="filter-roles" class="filter-input">
103
+ </div>""",
104
+ "content_type": """<div class="filter-group">
105
+ <label class="filter-label">Content Type</label>
106
+ <input type="text" id="filter-content-type" class="filter-input">
107
+ </div>""",
108
+ "params": """<div class="filter-group">
109
+ <label class="filter-label">Query Parameters</label>
110
+ <input type="text" id="filter-params" class="filter-input">
111
+ </div>""",
112
+ "schema": """<div class="filter-group">
113
+ <label class="filter-label">Schema Fields</label>
114
+ <input type="text" id="filter-schema" class="filter-input">
115
+ </div>""",
116
+ "pagination": """<div class="filter-group">
117
+ <label class="filter-label">Pagination Support</label>
118
+ <select id="filter-pagination" class="filter-select">
119
+ <option value="">All</option>
120
+ <option value="true">Yes</option>
121
+ <option value="false">No</option>
122
+ </select>
123
+ </div>""",
124
+ "ordering": """<div class="filter-group">
125
+ <label class="filter-label">Ordering Support</label>
126
+ <select id="filter-ordering" class="filter-select">
127
+ <option value="">All</option>
128
+ <option value="true">Yes</option>
129
+ <option value="false">No</option>
130
+ </select>
131
+ </div>""",
132
+ "search": """<div class="filter-group">
133
+ <label class="filter-label">Search Support</label>
134
+ <select id="filter-search" class="filter-select">
135
+ <option value="">All</option>
136
+ <option value="true">Yes</option>
137
+ <option value="false">No</option>
138
+ </select>
139
+ </div>""",
140
+ "tags": """<div class="filter-group">
141
+ <label class="filter-label">Tags</label>
142
+ <input type="text" id="filter-tags" class="filter-input">
143
+ </div>""",
144
+ }
145
+
146
+ fields_html = "\n".join(
147
+ [html for key, html in filter_fields.items() if (key in self.active_filters)]
148
+ )
149
+
150
+ return f"""
151
+ <div class="filter-sidebar collapsed" id="filterSidebar">
152
+ <h3 class="filter-title">🔍 Filters</h3>
153
+ <div class="filter-grid">
154
+ {fields_html}
155
+ </div>
156
+
157
+ <div class="filter-actions">
158
+ <button class="filter-apply" onclick="applyFilters()">Apply</button>
159
+ <button class="filter-clear" onclick="clearFilters()">Clear</button>
160
+ </div>
161
+
162
+ <div class="filter-results">Showing 0 endpoints</div>
163
+ </div>
164
+ """
165
+
166
+ def create_endpoints_index(
167
+ self, endpoints_by_app: dict[str, list[dict[str, Any]]], docs_dir: Path
168
+ ) -> None:
169
+ stylesheets = [
170
+ "stylesheets/endpoints/variables.css",
171
+ "stylesheets/endpoints/base.css",
172
+ "stylesheets/endpoints/theme-toggle.css",
173
+ "stylesheets/endpoints/filter-section.css",
174
+ "stylesheets/endpoints/layout.css",
175
+ "stylesheets/endpoints/endpoints-grid.css",
176
+ "stylesheets/endpoints/badges.css",
177
+ "stylesheets/endpoints/endpoint-content.css",
178
+ "stylesheets/endpoints/tags.css",
179
+ "stylesheets/endpoints/sections.css",
180
+ "stylesheets/endpoints/stats.css",
181
+ "stylesheets/endpoints/loading.css",
182
+ "stylesheets/endpoints/animations.css",
183
+ "stylesheets/endpoints/responsive.css",
184
+ "stylesheets/endpoints/accessibility.css",
185
+ "stylesheets/endpoints/fixes.css",
186
+ ]
187
+
188
+ scripts = [
189
+ "javascripts/endpoints-filter.js",
190
+ ]
191
+ prefix_path = f"{drf_to_mkdoc_settings.PROJECT_NAME}/"
192
+ css_links = "\n".join(
193
+ f'<link rel="stylesheet" href="{static(prefix_path + path)}">'
194
+ for path in stylesheets
195
+ )
196
+ js_scripts = "\n".join(
197
+ f'<script src="{static(prefix_path + path)}" defer></script>' for path in scripts
198
+ )
199
+
200
+ content = f"""# API Endpoints
201
+ <!-- inject CSS and JS directly -->
202
+ {css_links}
203
+ {js_scripts}
204
+
205
+ <div class="main-content">
206
+ """
207
+ content += self.create_filter_section()
208
+
209
+ for app_name, endpoints in endpoints_by_app.items():
210
+ content += f'<h2>{app_name.title()}</h2>\n<div class="endpoints-grid">\n'
211
+ for endpoint in endpoints:
212
+ viewset = endpoint["viewset"]
213
+ content += self.create_endpoint_card(endpoint, app_name, viewset)
214
+ content += "</div>\n"
215
+
216
+ content += "</div>\n"
217
+ output_path = docs_dir / "endpoints" / "index.md"
218
+ output_path.parent.mkdir(parents=True, exist_ok=True)
219
+ with Path(output_path).open("w", encoding="utf-8") as f:
220
+ f.write(content)
221
+
222
+
223
+ def create_endpoints_index(
224
+ endpoints_by_app: dict[str, list[dict[str, Any]]], docs_dir: Path
225
+ ) -> None:
226
+ generator = EndpointsIndexGenerator(
227
+ active_filters=[
228
+ "method",
229
+ "path",
230
+ "app",
231
+ "search",
232
+ ]
233
+ )
234
+ generator.create_endpoints_index(endpoints_by_app, docs_dir)
@@ -1,9 +1,7 @@
1
- #!/usr/bin/env python3
2
-
3
- """Query parameter extraction utilities for Django views."""
4
-
5
1
  from typing import Any
6
2
 
3
+ import django_filters
4
+
7
5
  from drf_to_mkdoc.utils.common import extract_viewset_from_operation_id
8
6
 
9
7
 
@@ -51,7 +49,7 @@ def extract_query_parameters_from_view_filter_fields(view_class: Any) -> list[st
51
49
  elif hasattr(view_class, "filterset_fields") and view_class.filterset_fields:
52
50
  filter_fields = sorted(view_class.filterset_fields)
53
51
 
54
- return filter_fields
52
+ return list(set(filter_fields))
55
53
 
56
54
 
57
55
  def extract_query_parameters_from_view_ordering_fields(view_class: Any) -> list[str]:
@@ -116,8 +114,6 @@ def _extract_filterset_fields_from_class_attributes(filterset_class: Any) -> lis
116
114
  fields = []
117
115
 
118
116
  try:
119
- import django_filters
120
-
121
117
  # Get all class attributes, including inherited ones
122
118
  for attr_name in dir(filterset_class):
123
119
  # Skip private attributes and known non-filter attributes
@@ -186,18 +182,21 @@ def _extract_filterset_fields_from_internal_attrs(filterset_class: Any) -> list[
186
182
 
187
183
 
188
184
  def _extract_filterset_fields_from_get_fields(filterset_class: Any) -> list[str]:
189
- fields = []
185
+ if not (filterset_class._meta and filterset_class._meta.model):
186
+ # If the Meta class is not defined in the Filter class,
187
+ # the get_fields function is raise error
188
+ return []
190
189
 
191
190
  # Try get_fields() method if available (for dynamic filters)
192
- if hasattr(filterset_class, "get_fields"):
193
- filterset_instance = filterset_class()
194
- filterset_fields = filterset_instance.get_fields()
195
- if filterset_fields and hasattr(filterset_fields, "keys"):
196
- for field in filterset_fields:
197
- if field not in fields:
198
- fields.append(field)
191
+ if not hasattr(filterset_class, "get_fields"):
192
+ return []
199
193
 
200
- return fields
194
+ filterset_instance = filterset_class()
195
+ filterset_fields = filterset_instance.get_fields()
196
+ if not (filterset_fields and hasattr(filterset_fields, "keys")):
197
+ return []
198
+
199
+ return list(set(filterset_fields))
201
200
 
202
201
 
203
202
  def extract_filterset_fields(filterset_class: Any) -> list[str]:
@@ -1,55 +1,9 @@
1
- from pathlib import Path
2
1
  from typing import Any
3
2
 
4
- from drf_to_mkdoc.utils.common import get_app_descriptions, get_model_description, write_file
3
+ from django.templatetags.static import static
5
4
 
6
-
7
- def create_models_index(models_data: dict[str, Any], docs_dir: Path) -> None:
8
- models_by_app = {}
9
- for model_name, model_info in models_data.items():
10
- app_name = model_info.get("app_label", model_name.split(".")[0])
11
- class_name = model_info.get("name", model_name.split(".")[-1])
12
- if app_name not in models_by_app:
13
- models_by_app[app_name] = []
14
- models_by_app[app_name].append((class_name, model_name, model_info))
15
-
16
- content = """# Django Models\n\nThis section contains documentation for
17
- all Django models in the system, organized by Django application.\n\n"""
18
-
19
- app_descriptions = get_app_descriptions()
20
-
21
- for app_name in sorted(models_by_app.keys()):
22
- app_desc = app_descriptions.get(app_name, f"{app_name.title()} application models")
23
- content += f'<div class="app-header">{app_name.title()} App</div>\n\n'
24
- content += f"*{app_desc}*\n\n"
25
-
26
- content += '<div class="model-cards">\n'
27
-
28
- for class_name, _model_name, _model_info in sorted(models_by_app[app_name]):
29
- content += f"""
30
- <a href="{app_name}/{class_name.lower()}/"
31
- class="model-card">{class_name}</a>\n
32
- """
33
-
34
- content += "</div>\n\n"
35
-
36
- content += """## Model Relationships\n\nThe models are interconnected through foreign keys
37
- and many-to-many relationships:\n\n- **Users** can be associated
38
- with multiple **Clinics** through **ClinicUser**
39
- \n- **Doctors** belong to **Clinics**
40
- and offer **Services** through **DoctorService**
41
- \n- **Appointments** connect **Patients**
42
- with **Doctors** and **Services**
43
- \n- **Schedules** define **Doctor** availability in specific **Rooms**
44
- \n- **Rooms** belong to **Clinics** and host **Appointments**\n
45
- \nEach model page contains detailed field documentation,
46
- method signatures, and relationships to other models.\n"""
47
-
48
- models_index_path = docs_dir / "models" / "index.md"
49
- models_index_path.parent.mkdir(parents=True, exist_ok=True)
50
-
51
- with models_index_path.open("w", encoding="utf-8") as f:
52
- f.write(content)
5
+ from drf_to_mkdoc.conf.settings import drf_to_mkdoc_settings
6
+ from drf_to_mkdoc.utils.common import get_model_description, write_file
53
7
 
54
8
 
55
9
  def generate_model_docs(models_data: dict[str, Any]) -> None:
@@ -67,6 +21,7 @@ def generate_model_docs(models_data: dict[str, Any]) -> None:
67
21
 
68
22
 
69
23
  def render_fields_table(fields: dict[str, Any]) -> str:
24
+ """Render the fields table for a model."""
70
25
  content = "## Fields\n\n"
71
26
  content += "| Field | Type | Description | Extra |\n"
72
27
  content += "|-------|------|-------------|-------|\n"
@@ -102,6 +57,7 @@ def render_fields_table(fields: dict[str, Any]) -> str:
102
57
 
103
58
 
104
59
  def render_choices_tables(fields: dict[str, Any]) -> str:
60
+ """Render choice tables for fields with choices."""
105
61
  choice_tables = []
106
62
 
107
63
  for field_name, field_info in fields.items():
@@ -138,10 +94,23 @@ def create_model_page(model_info: dict[str, Any]) -> str:
138
94
 
139
95
  def _create_model_header(name: str, app_label: str, table_name: str, description: str) -> str:
140
96
  """Create the header section of the model documentation."""
97
+ stylesheets = [
98
+ "stylesheets/models/variables.css",
99
+ "stylesheets/models/base.css",
100
+ "stylesheets/models/model-tables.css",
101
+ "stylesheets/models/responsive.css",
102
+ ]
103
+ prefix_path = f"{drf_to_mkdoc_settings.PROJECT_NAME}/"
104
+ css_links = "\n".join(
105
+ f'<link rel="stylesheet" href="{static(prefix_path + path)}">' for path in stylesheets
106
+ )
141
107
  return f"""# {name}
142
108
 
143
- **App:** {app_label}\n
144
- **Table:** `{table_name}`\n
109
+ <!-- inject CSS directly -->
110
+ {css_links}
111
+
112
+ **App:** {app_label}
113
+ **Table:** `{table_name}`
145
114
 
146
115
  ## Description
147
116
 
@@ -0,0 +1,67 @@
1
+ from pathlib import Path
2
+ from typing import Any
3
+
4
+ from django.templatetags.static import static
5
+
6
+ from drf_to_mkdoc.conf.settings import drf_to_mkdoc_settings
7
+ from drf_to_mkdoc.utils.common import get_app_descriptions
8
+
9
+
10
+ def create_models_index(models_data: dict[str, Any], docs_dir: Path) -> None:
11
+ """Create the main models index page that lists all models organized by app."""
12
+ models_by_app = {}
13
+ for model_name, model_info in models_data.items():
14
+ app_name = model_info.get("app_label", model_name.split(".")[0])
15
+ class_name = model_info.get("name", model_name.split(".")[-1])
16
+ if app_name not in models_by_app:
17
+ models_by_app[app_name] = []
18
+ models_by_app[app_name].append((class_name, model_name, model_info))
19
+
20
+ stylesheets = [
21
+ "stylesheets/models/variables.css",
22
+ "stylesheets/models/base.css",
23
+ "stylesheets/models/model-cards.css",
24
+ "stylesheets/models/responsive.css",
25
+ "stylesheets/models/animations.css",
26
+ ]
27
+ prefix_path = f"{drf_to_mkdoc_settings.PROJECT_NAME}/"
28
+ css_links = "\n".join(
29
+ f'<link rel="stylesheet" href="{static(prefix_path + path)}">' for path in stylesheets
30
+ )
31
+ content = f"""# Django Models
32
+
33
+ This section contains documentation for all Django models in the system, organized by Django application.
34
+
35
+ <!-- inject CSS directly -->
36
+ {css_links}
37
+
38
+ <div class="models-container">
39
+ """
40
+
41
+ app_descriptions = get_app_descriptions()
42
+
43
+ for app_name in sorted(models_by_app.keys()):
44
+ app_desc = app_descriptions.get(app_name, f"{app_name.title()} application models")
45
+ content += f'<div class="app-header">{app_name.title()} App</div>\n'
46
+ content += f'<div class="app-description">{app_desc}</div>\n\n'
47
+
48
+ content += '<div class="model-cards">\n'
49
+
50
+ for class_name, _model_name, _model_info in sorted(models_by_app[app_name]):
51
+ content += f"""
52
+ <a href="{app_name}/{class_name.lower()}/"
53
+ class="model-card">{class_name}</a>\n
54
+ """
55
+
56
+ content += "</div>\n\n"
57
+
58
+ content += """</div>
59
+
60
+
61
+ Each model page contains detailed field documentation, method signatures, and relationships to other models."""
62
+
63
+ models_index_path = docs_dir / "models" / "index.md"
64
+ models_index_path.parent.mkdir(parents=True, exist_ok=True)
65
+
66
+ with models_index_path.open("w", encoding="utf-8") as f:
67
+ f.write(content)
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: drf-to-mkdoc
3
- Version: 0.1.5
3
+ Version: 0.1.8
4
4
  Summary: Generate Markdown API docs from Django/DRF OpenAPI schema for MkDocs
5
5
  Author-email: Hossein Shayesteh <shayestehhs1@gmail.com>
6
6
  Maintainer-email: Hossein Shayesteh <shayestehhs1@gmail.com>
@@ -101,30 +101,8 @@ DRF_TO_MKDOC = {
101
101
  }
102
102
  ```
103
103
 
104
- 2. **Create MkDocs configuration**:
105
-
106
- ```yaml
107
- # mkdocs.yml
108
- site_name: Your API Documentation
109
- theme:
110
- name: material
111
- features:
112
- - navigation.tabs
113
- - navigation.sections
114
- - navigation.expand
115
- - search.highlight
116
- - search.share
117
-
118
- plugins:
119
- - search
120
-
121
- nav:
122
- - Home: index.md
123
- - About: about.md
124
- - Models: models/index.md
125
- - API Endpoints: endpoints/index.md
126
- - Pagination: pagination.md
127
- ```
104
+ 2. **Create MkDocs configuration**:
105
+ Copy the [`docs/mkdocs.yml`](docs/mkdocs.yml) file to your project root and customize it as needed.
128
106
 
129
107
  3. **Build documentation**:
130
108
 
@@ -0,0 +1,50 @@
1
+ drf_to_mkdoc/__init__.py,sha256=IbTW5uKQvJRG9ncHRuk_AGKHPn4ruxs5LqDpUFgUhws,180
2
+ drf_to_mkdoc/apps.py,sha256=-NrC_dRr6GmLmNQhkNh819B7V1SS4DYDv5JOR0TtuJM,560
3
+ drf_to_mkdoc/conf/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
4
+ drf_to_mkdoc/conf/defaults.py,sha256=hEjQdN3WsT539UWhFkylI60piykV_7BDudLPNd_E8PE,575
5
+ drf_to_mkdoc/conf/settings.py,sha256=OOna4jWNTEfROBprpKnEHVl5RcAYExmOf0gBMA0E_FY,1664
6
+ drf_to_mkdoc/management/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
7
+ drf_to_mkdoc/management/commands/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
8
+ drf_to_mkdoc/management/commands/build_docs.py,sha256=71dDDbb-qjRZr0kugviHtf3W_MSPFVjxkJ0tlLn97zM,4037
9
+ drf_to_mkdoc/management/commands/generate_doc_json.py,sha256=mWdYgMbSeLP4iQZeUm2DxwYQmdGy8w05XTEfbT_nOJo,19833
10
+ drf_to_mkdoc/management/commands/generate_docs.py,sha256=LUvKeJQ_cDL48rEfbWyjDsYEwzkQEpxpEjqUm11zQJg,5011
11
+ drf_to_mkdoc/management/commands/generate_model_docs.py,sha256=A_Q6o10kfy-GN_ZDD9YS6jv3RTyxBy28DEsi5qKZZoU,13421
12
+ drf_to_mkdoc/management/commands/update_doc_schema.py,sha256=TtHVQxnVpB_VELRkVcdsDXDU5zXdguFleB1mXCDMAbg,2009
13
+ drf_to_mkdoc/static/drf-to-mkdoc/javascripts/endpoints-filter.js,sha256=KtfWroqsXg-wwmk36hpoH--M9WIW85EFNGeswMjFu4g,6138
14
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/accessibility.css,sha256=DwCGPoaxaUvyifryrKqmkFDH06XBNf65kYsflMTbi0M,494
15
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/animations.css,sha256=61m9SLAbatVUNuFeTUTxktoMu9SskYcwFjTsHYbsCRo,393
16
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/badges.css,sha256=kUlUcf72uRw6x6Gn7cUq_aTuSGBbhumZ4Us-eBDM7DM,1251
17
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/base.css,sha256=K9lEjO-TEaUsFCaiuBwqDGrrjIJP8oBDh7igBGRTD3g,1839
18
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/endpoint-content.css,sha256=1EKHfDeOSpNJe6l3mHzsBlLqLVCJn_1TKtEVfV7Dp88,3452
19
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/endpoints-grid.css,sha256=Ct4H_ma3tC_1ogw9IeSNmUDZFJwzQWjCM6GomNXV8ig,4115
20
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/filter-section.css,sha256=MDsGVwgFMhP28pegPLJFn3_GJqVSWZAoy6quz5_9Gz0,4424
21
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/fixes.css,sha256=MIPiwWXkSMt5I_q6jN6X5CvWTBmq1CERKZffhvf3sKM,720
22
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/layout.css,sha256=dyoTUJ5Y8njxdWE6t2G3nRS-bT0BT04UMat8K6yW2y4,637
23
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/loading.css,sha256=C_wZjMw5Cs2inpg892S0_E7_m5bT8BwZfVBRQfvIcKw,712
24
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/responsive.css,sha256=mzR4tB3XrCg6Ih-X5GEzXzZoSR0R0AEKArRIZ7LqiGU,1672
25
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/sections.css,sha256=xdrO6vUpthFFN1ESummoGuG5MPtE2d2lPsBOWuv-T6o,705
26
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/stats.css,sha256=0cDD8s63r6zQid_O1schNvfIwys1Y526xO6-B6s4Lxc,667
27
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/tags.css,sha256=dOw13qsvVjx9cibzgzXlOutXVosNp6LzFfEFKvumG8w,1785
28
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/theme-toggle.css,sha256=j1P5xDQDfos8jeVYz5s1jjEeujMlZtLi39OC6VeuMcA,1034
29
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/endpoints/variables.css,sha256=Sg2vcQOHdpmEFDn43OeZcMIKxtr5EOEI_wISkCmtcSU,1895
30
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/models/animations.css,sha256=IrqN9vJKgaHAWk2PBRKKmFHgH-lQlw5YZvEOGDqYk_g,656
31
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/models/base.css,sha256=qdXDVScWoEvFbSRfjDlnxvQZBy2JFX9yXPngMWNSZ7o,1849
32
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/models/model-cards.css,sha256=IppCOptBoFeQCz2sc-exPrnxvsdDxcwYGM-foQrZoVU,2779
33
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/models/model-tables.css,sha256=8CSy8YdFOJ3lGZ3sTVz2jd8cIxIryubQFrwcygAw06w,1352
34
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/models/responsive.css,sha256=ygqyUtpiWchTBBIQil1C6mN0AC5xinLoP7whSKfBmwg,944
35
+ drf_to_mkdoc/static/drf-to-mkdoc/stylesheets/models/variables.css,sha256=2HvyjnJrygSzdzpE-FYpo6FGhrYhmZ7NwDFAkADXQNg,1094
36
+ drf_to_mkdoc/utils/__init__.py,sha256=6dFTb07S6yIf-INMy0Mlgf5purNir687ZU9WZtITh4k,68
37
+ drf_to_mkdoc/utils/common.py,sha256=qPF7tfnEsRbf57JJwDCqMtjMFmxmpWguXPQabHkag70,11711
38
+ drf_to_mkdoc/utils/endpoint_detail_generator.py,sha256=mX3sklhWsd-FmOV-ePrhLpg5l8-Eu7V7qb5EL4Tq0FI,27650
39
+ drf_to_mkdoc/utils/endpoint_list_generator.py,sha256=P7pEHscHNHpjDuTXmAUPYV3_t8uGSdaYOgiDGGoCwYc,9705
40
+ drf_to_mkdoc/utils/model_detail_generator.py,sha256=P5kWO-5aWgvyPgzq1qXnt1380ExnrzlOw18zI57P9u0,8063
41
+ drf_to_mkdoc/utils/model_list_generator.py,sha256=7gTPwxOxlvvCfDgVPTbGPsLi1gnI47UjMqKc57qRmks,2409
42
+ drf_to_mkdoc/utils/extractors/__init__.py,sha256=BvC8gKOPVI9gU1Piw0jRhKQ2ER5s1moAxgq7ZYkJWNI,86
43
+ drf_to_mkdoc/utils/extractors/query_parameter_extractors.py,sha256=gnDlvF-bxkTp2NcEQf0EZZAfmdQzUpedhZ7N1LAYQzU,8432
44
+ drf_to_mkdoc/utils/md_generators/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
45
+ drf_to_mkdoc/utils/md_generators/query_parameters_generators.py,sha256=N-XqZ_FUODSR5V4xM9oEA3aaIiNGNmNwpvrWbQTx6RI,2566
46
+ drf_to_mkdoc-0.1.8.dist-info/licenses/LICENSE,sha256=3n9_ckIREsH8ogCxWW6dFsw_WfGcluG2mHcgl9i_UU0,1068
47
+ drf_to_mkdoc-0.1.8.dist-info/METADATA,sha256=A_y3wLQBP6TCyeuv40sF-iqeD-UEYLzXQwUTdeem1dI,7037
48
+ drf_to_mkdoc-0.1.8.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
49
+ drf_to_mkdoc-0.1.8.dist-info/top_level.txt,sha256=ZzJecR6j_tvLZiubUBEgawHflozC4DQy9ooNf1yDJ3Q,13
50
+ drf_to_mkdoc-0.1.8.dist-info/RECORD,,
@@ -1,25 +0,0 @@
1
- drf_to_mkdoc/__init__.py,sha256=j7qOxIbkDy7oit4Tb3NZUqbqkrxKz07PeN9QuF3Qp9s,179
2
- drf_to_mkdoc/apps.py,sha256=0TLecPHZ8vf0IhAVFh1oIIHQbhx5lVto7qrvStx3R1Y,464
3
- drf_to_mkdoc/conf/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
4
- drf_to_mkdoc/conf/defaults.py,sha256=9OK65SeP4aLZbuRJBAE_QeC-OhXkh0cACBqax6wYXnM,576
5
- drf_to_mkdoc/conf/settings.py,sha256=OgB3MCn4Z5F4xqWP34kwzMs50kRn3qF0gE1zS2SHS2M,1550
6
- drf_to_mkdoc/management/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
7
- drf_to_mkdoc/management/commands/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
8
- drf_to_mkdoc/management/commands/build_docs.py,sha256=p--TajkpYU-hmthXp5eVmVtJnXLxZrfQWQmuzwOgl0c,2491
9
- drf_to_mkdoc/management/commands/generate_doc_json.py,sha256=mWdYgMbSeLP4iQZeUm2DxwYQmdGy8w05XTEfbT_nOJo,19833
10
- drf_to_mkdoc/management/commands/generate_docs.py,sha256=YGdejd-b1Wn_e5ru9orwp1b9H5PZwVWkuWxAY1JyG88,4897
11
- drf_to_mkdoc/management/commands/generate_model_docs.py,sha256=tdT9Z0qjZ9KgGAbFfYWBo-FtDI8wTQ2zRA_OvKKnyaA,12195
12
- drf_to_mkdoc/management/commands/update_doc_schema.py,sha256=TtHVQxnVpB_VELRkVcdsDXDU5zXdguFleB1mXCDMAbg,2009
13
- drf_to_mkdoc/utils/__init__.py,sha256=6dFTb07S6yIf-INMy0Mlgf5purNir687ZU9WZtITh4k,68
14
- drf_to_mkdoc/utils/common.py,sha256=BIzN9iDOphIHPGkRGj8iVhY8lAUdvBAyNazP3wDmz9c,11814
15
- drf_to_mkdoc/utils/endpoint_generator.py,sha256=oGHQXJB5VFlGOq6W8a3q96CwF3conjBe_tkYj6m2mlg,35849
16
- drf_to_mkdoc/utils/model_generator.py,sha256=O1ibaw7KmL_fQ1OTebuk6Tt2yTjyElpyF7bN8gk5LBE,9588
17
- drf_to_mkdoc/utils/extractors/__init__.py,sha256=BvC8gKOPVI9gU1Piw0jRhKQ2ER5s1moAxgq7ZYkJWNI,86
18
- drf_to_mkdoc/utils/extractors/query_parameter_extractors.py,sha256=e7WW0MeLUfBAfksEKFxowDjz9uUvit_EDxYASfnbdc4,8400
19
- drf_to_mkdoc/utils/md_generators/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
20
- drf_to_mkdoc/utils/md_generators/query_parameters_generators.py,sha256=N-XqZ_FUODSR5V4xM9oEA3aaIiNGNmNwpvrWbQTx6RI,2566
21
- drf_to_mkdoc-0.1.5.dist-info/licenses/LICENSE,sha256=3n9_ckIREsH8ogCxWW6dFsw_WfGcluG2mHcgl9i_UU0,1068
22
- drf_to_mkdoc-0.1.5.dist-info/METADATA,sha256=qFgbvjEKTuW_DP6VlK3YsJZGIg1NYY1b35j5TdQ4YZU,7304
23
- drf_to_mkdoc-0.1.5.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
24
- drf_to_mkdoc-0.1.5.dist-info/top_level.txt,sha256=ZzJecR6j_tvLZiubUBEgawHflozC4DQy9ooNf1yDJ3Q,13
25
- drf_to_mkdoc-0.1.5.dist-info/RECORD,,