适配linux系统
This commit is contained in:
@@ -2,8 +2,16 @@
|
|||||||
HTML-based Frame Generator Service
|
HTML-based Frame Generator Service
|
||||||
|
|
||||||
Renders HTML templates to frame images with variable substitution
|
Renders HTML templates to frame images with variable substitution
|
||||||
|
|
||||||
|
Linux Environment Requirements:
|
||||||
|
- fontconfig package must be installed
|
||||||
|
- Basic fonts (e.g., fonts-liberation, fonts-noto) recommended
|
||||||
|
|
||||||
|
Ubuntu/Debian: sudo apt-get install -y fontconfig fonts-liberation fonts-noto-cjk
|
||||||
|
CentOS/RHEL: sudo yum install -y fontconfig liberation-fonts google-noto-cjk-fonts
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
import os
|
||||||
import uuid
|
import uuid
|
||||||
from typing import Dict, Any, Optional
|
from typing import Dict, Any, Optional
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
@@ -38,8 +46,45 @@ class HTMLFrameGenerator:
|
|||||||
self.template_path = template_path
|
self.template_path = template_path
|
||||||
self.template = self._load_template(template_path)
|
self.template = self._load_template(template_path)
|
||||||
self.hti = None # Lazy init to avoid overhead
|
self.hti = None # Lazy init to avoid overhead
|
||||||
|
self._check_linux_dependencies()
|
||||||
logger.debug(f"Loaded HTML template: {template_path}")
|
logger.debug(f"Loaded HTML template: {template_path}")
|
||||||
|
|
||||||
|
def _check_linux_dependencies(self):
|
||||||
|
"""Check Linux system dependencies and warn if missing"""
|
||||||
|
if os.name != 'posix':
|
||||||
|
return
|
||||||
|
|
||||||
|
try:
|
||||||
|
import subprocess
|
||||||
|
|
||||||
|
# Check fontconfig
|
||||||
|
result = subprocess.run(
|
||||||
|
['fc-list'],
|
||||||
|
capture_output=True,
|
||||||
|
timeout=2
|
||||||
|
)
|
||||||
|
|
||||||
|
if result.returncode != 0:
|
||||||
|
logger.warning(
|
||||||
|
"⚠️ fontconfig not found or not working properly. "
|
||||||
|
"Install with: sudo apt-get install -y fontconfig fonts-liberation fonts-noto-cjk"
|
||||||
|
)
|
||||||
|
elif not result.stdout:
|
||||||
|
logger.warning(
|
||||||
|
"⚠️ No fonts detected by fontconfig. "
|
||||||
|
"Install fonts with: sudo apt-get install -y fonts-liberation fonts-noto-cjk"
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
logger.debug(f"✓ Fontconfig detected {len(result.stdout.splitlines())} fonts")
|
||||||
|
|
||||||
|
except FileNotFoundError:
|
||||||
|
logger.warning(
|
||||||
|
"⚠️ fontconfig (fc-list) not found on system. "
|
||||||
|
"Install with: sudo apt-get install -y fontconfig"
|
||||||
|
)
|
||||||
|
except Exception as e:
|
||||||
|
logger.debug(f"Could not check fontconfig status: {e}")
|
||||||
|
|
||||||
def _load_template(self, template_path: str) -> str:
|
def _load_template(self, template_path: str) -> str:
|
||||||
"""Load HTML template from file"""
|
"""Load HTML template from file"""
|
||||||
path = Path(template_path)
|
path = Path(template_path)
|
||||||
@@ -55,8 +100,31 @@ class HTMLFrameGenerator:
|
|||||||
def _ensure_hti(self, width: int, height: int):
|
def _ensure_hti(self, width: int, height: int):
|
||||||
"""Lazily initialize Html2Image instance"""
|
"""Lazily initialize Html2Image instance"""
|
||||||
if self.hti is None:
|
if self.hti is None:
|
||||||
self.hti = Html2Image(size=(width, height))
|
# Configure Chrome flags for Linux headless environment
|
||||||
logger.debug(f"Initialized Html2Image with size ({width}, {height})")
|
custom_flags = [
|
||||||
|
'--no-sandbox', # Bypass AppArmor/sandbox restrictions
|
||||||
|
'--disable-dev-shm-usage', # Avoid shared memory issues
|
||||||
|
'--disable-gpu', # Disable GPU acceleration
|
||||||
|
'--disable-software-rasterizer', # Disable software rasterizer
|
||||||
|
'--disable-extensions', # Disable extensions
|
||||||
|
'--disable-setuid-sandbox', # Additional sandbox bypass
|
||||||
|
'--disable-dbus', # Disable DBus to avoid permission errors
|
||||||
|
'--hide-scrollbars', # Hide scrollbars for cleaner output
|
||||||
|
'--mute-audio', # Mute audio
|
||||||
|
'--disable-background-networking', # Disable background networking
|
||||||
|
'--disable-features=TranslateUI', # Disable translate UI
|
||||||
|
'--disable-ipc-flooding-protection', # Improve performance
|
||||||
|
'--no-first-run', # Skip first run dialogs
|
||||||
|
'--no-default-browser-check', # Skip default browser check
|
||||||
|
'--disable-backgrounding-occluded-windows', # Improve performance
|
||||||
|
'--disable-renderer-backgrounding', # Improve performance
|
||||||
|
]
|
||||||
|
|
||||||
|
self.hti = Html2Image(
|
||||||
|
size=(width, height),
|
||||||
|
custom_flags=custom_flags
|
||||||
|
)
|
||||||
|
logger.debug(f"Initialized Html2Image with size ({width}, {height}) and {len(custom_flags)} custom flags")
|
||||||
|
|
||||||
async def generate_frame(
|
async def generate_frame(
|
||||||
self,
|
self,
|
||||||
|
|||||||
Reference in New Issue
Block a user