100 lines
4.1 KiB
Python
100 lines
4.1 KiB
Python
from django.core.management.base import BaseCommand
|
|
from django.urls import get_resolver
|
|
import os
|
|
import json
|
|
from django.template.loaders.app_directories import get_app_template_dirs
|
|
|
|
|
|
class Command(BaseCommand):
|
|
help = "Generate UI element map for IntroJS tours"
|
|
|
|
def handle(self, *args, **kwargs):
|
|
output_file = os.path.join("static", "js", "tours", "ui_element_map.json")
|
|
|
|
ui_map = {
|
|
"pages": {},
|
|
"common_elements": {
|
|
"navigation": {
|
|
"inventory": "#inventory-menu, .inventory-nav, nav .inventory",
|
|
"finance": "#finance-menu, .finance-nav, nav .finance",
|
|
"customers": "#customers-menu, .customers-nav, nav .customers",
|
|
},
|
|
"actions": {
|
|
"add": ".btn-add, .add-button, button:contains('Add')",
|
|
"edit": ".btn-edit, .edit-button, button:contains('Edit')",
|
|
"save": ".btn-save, button[type='submit'], #save-button",
|
|
"cancel": ".btn-cancel, #cancel-button, button:contains('Cancel')",
|
|
"delete": ".btn-delete, .delete-button, button:contains('Delete')",
|
|
},
|
|
"forms": {
|
|
"search": "#search-form, .search-input, input[name='q']",
|
|
"date_range": ".date-range, input[type='date']",
|
|
"dropdown": "select, .dropdown, .select-field",
|
|
},
|
|
},
|
|
}
|
|
|
|
# Extract URL patterns to identify pages
|
|
resolver = get_resolver()
|
|
for url_pattern in resolver.url_patterns:
|
|
if hasattr(url_pattern, "name") and url_pattern.name:
|
|
pattern_name = url_pattern.name
|
|
# Skip admin and API URLs
|
|
if pattern_name.startswith(("admin:", "api:")):
|
|
continue
|
|
|
|
ui_map["pages"][pattern_name] = {
|
|
"url_pattern": str(url_pattern.pattern),
|
|
"elements": {},
|
|
}
|
|
|
|
# Scan templates for UI elements with IDs
|
|
template_dirs = get_app_template_dirs("templates")
|
|
for template_dir in template_dirs:
|
|
for root, dirs, files in os.walk(template_dir):
|
|
for file in files:
|
|
if not file.endswith((".html", ".htm")):
|
|
continue
|
|
|
|
try:
|
|
with open(os.path.join(root, file), "r", encoding="utf-8") as f:
|
|
content = f.read()
|
|
|
|
# Try to identify the page/view this template is for
|
|
template_path = os.path.relpath(
|
|
os.path.join(root, file), template_dir
|
|
)
|
|
page_key = template_path.replace("/", "_").replace(
|
|
".html", ""
|
|
)
|
|
|
|
# Create page entry if it doesn't exist
|
|
if page_key not in ui_map["pages"]:
|
|
ui_map["pages"][page_key] = {
|
|
"template": template_path,
|
|
"elements": {},
|
|
}
|
|
|
|
# Extract elements with IDs
|
|
import re
|
|
|
|
id_matches = re.findall(r'id=["\']([^"\']+)["\']', content)
|
|
for id_match in id_matches:
|
|
ui_map["pages"][page_key]["elements"][id_match] = (
|
|
f"#{id_match}"
|
|
)
|
|
|
|
except Exception as e:
|
|
self.stdout.write(
|
|
self.style.WARNING(f"Error processing template {file}: {e}")
|
|
)
|
|
|
|
# Save UI map as JSON
|
|
os.makedirs(os.path.dirname(output_file), exist_ok=True)
|
|
with open(output_file, "w", encoding="utf-8") as f:
|
|
json.dump(ui_map, f, indent=2)
|
|
|
|
self.stdout.write(
|
|
self.style.SUCCESS(f"✅ UI element map saved to {output_file}")
|
|
)
|