在无GUI Linux(含Docker)及跨平台环境中使用Python Plotly加载本地TTF字体生成多语言SVG图表的技术问询
I ran into this exact issue when deploying Plotly charts in a headless Docker environment, so here are two reliable solutions that work across Windows, Mac, and headless Linux/Docker setups. The core problem is that Plotly's font.family parameter expects a font name, not a direct file path—we need to make the font recognizable to Plotly first.
Option 1: Register the Font with Matplotlib's Font Manager
This method registers your TTF file with matplotlib's font database, making its official name available to Plotly. It’s cross-platform and doesn’t require extra config for Plotly’s renderer.
import plotly.graph_objects as go import numpy as np from matplotlib import font_manager # Path to your custom TTF font file font_path = "/usr/fonts/Noto Sans.ttf" # Load and register the font with matplotlib's font manager font_manager.fontManager.addfont(font_path) # Get the official font name (this is what Plotly will use, not the filename) font_name = font_manager.FontProperties(fname=font_path).get_name() # Create your plot as usual t = np.linspace(0, 10, 100) fig = go.Figure() fig.add_trace(go.Scatter( x=t, y=np.sin(t), name='sin', mode='markers', marker_color='rgba(152, 0, 0, .8)' )) # Update layout with the registered font name fig.update_layout( title='Styled Scatter', yaxis_zeroline=False, xaxis_zeroline=False, font=dict(family=font_name, size=18) ) # Save as SVG (requires kaleido to be installed) fig.write_image("scatter_plot.svg")
Notes for Option 1:
- Install matplotlib first if you haven’t:
pip install matplotlib - The official font name might differ from the filename (e.g., "Noto Sans.ttf" could have a name like "Noto Sans Regular"). Using
FontProperties.get_name()ensures you get the correct value.
Option 2: Configure Kaleido to Load Custom Fonts
Plotly uses Kaleido to export static images like SVG. You can directly tell Kaleido about your custom font files, which is ideal for Docker setups where you want to avoid matplotlib dependencies.
First, install Kaleido:
pip install kaleido
Then use this code:
import plotly.graph_objects as go import numpy as np from plotly.io._kaleido import ensure_kaleido # Define Kaleido config to add your custom font kaleido_config = { "fonts": { "custom_fonts": [ { "name": "Noto Sans", # The name you'll reference in Plotly "files": ["/usr/fonts/Noto Sans.ttf"] # Path to your TTF file } ] } } # Initialize Kaleido with the custom config kaleido = ensure_kaleido(config=kaleido_config) # Create your plot t = np.linspace(0, 10, 100) fig = go.Figure() fig.add_trace(go.Scatter( x=t, y=np.sin(t), name='sin', mode='markers', marker_color='rgba(152, 0, 0, .8)' )) # Use the font name defined in your Kaleido config fig.update_layout( title='Styled Scatter', yaxis_zeroline=False, xaxis_zeroline=False, font=dict(family="Noto Sans", size=18) ) # Save as SVG fig.write_image("scatter_plot.svg")
Notes for Option 2:
- In Docker, ensure your font file is accessible (mount it via
-vduring runtime or copy it into the image during build) - You can add multiple fonts to the
custom_fontslist if needed - This method keeps your Docker image lighter by skipping matplotlib
Cross-Platform Tips
- Always use absolute paths for font files to avoid path resolution issues
- For multi-language support (e.g., Chinese, Japanese), use fonts that cover the required character sets (like Noto Sans CJK SC)
- Test the font name first—print
font_name(Option 1) or double-check the name in your Kaleido config to ensure Plotly recognizes it
内容的提问来源于stack exchange,提问作者Ronak SHAH




