Files
ETPlot/test.ipynb
T
Kylian Schmidt 976d90f26b Refactor gallery generator with smart file handling and improved UI
Key improvements:
- Add intelligent file update checking with 30-second buffer to avoid unnecessary operations
- Implement efficient PDF to PNG conversion (only when source is newer)
- Add smart file copying (skip if target is up-to-date)
- Create proper folder structure using plot_root/source_name pattern
- Improve template with better text handling for long plot names
- Add text wrapping, truncation, and hover tooltips for plot names
- Remove unnecessary directory cleaning for true incremental updates
- Fix title display issue (was showing '.' instead of 'Gallery')
- Add comprehensive logging showing what's processed vs skipped

Performance benefits:
- Subsequent runs are significantly faster (only processes changed files)
- Reduces ImageMagick conversions and file I/O operations
- Maintains file system timing robustness with buffer delays

UI improvements:
- Better handling of long filenames with word wrapping
- Constrained text areas prevent overlap between thumbnails
- Hover tooltips show full names when truncated
- Responsive grid layout maintained
2025-07-07 13:27:25 +02:00

236 lines
7.0 KiB
Plaintext

{
"cells": [
{
"cell_type": "code",
"execution_count": 2,
"id": "aedbb9f5",
"metadata": {},
"outputs": [],
"source": [
"from dataclasses import dataclass, field, asdict\n",
"from pathlib import Path\n",
"\n",
"import yaml\n",
"\n",
"\n",
"@dataclass\n",
"class GalleryItem:\n",
" name: str\n",
" path: Path\n"
]
},
{
"cell_type": "code",
"execution_count": 5,
"id": "66624faf",
"metadata": {},
"outputs": [],
"source": [
"yaml_file = Path(\"config.yaml\")\n",
"\n",
"with open(yaml_file, \"r\") as f:\n",
" new_config: dict = yaml.safe_load(f)"
]
},
{
"cell_type": "code",
"execution_count": 8,
"id": "40a472f8",
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"{'name': 'test_1_plot',\n",
" 'path': 'data/cf_store/test_analysis/cf.PlotVariables1D/run2_2016_nano_v9/calib__test/sel__test/prod__test/weight__test/nominal/datasets_ttbar_dl/dev1/plot__proc_3_5606769559__cat_incl__var_jet1_pt.pdf'}"
]
},
"execution_count": 8,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"new_config[\"sources\"][0]"
]
},
{
"cell_type": "code",
"execution_count": 10,
"id": "745c97ad",
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"[GalleryItem(name='test_1_plot', path=PosixPath('data/cf_store/test_analysis/cf.PlotVariables1D/run2_2016_nano_v9/calib__test/sel__test/prod__test/weight__test/nominal/datasets_ttbar_dl/dev1/plot__proc_3_5606769559__cat_incl__var_jet1_pt.pdf')),\n",
" GalleryItem(name='test_2_dir', path=PosixPath('data/cf_store/test_analysis/cf.PlotVariables1D/run2_2016_nano_v9/calib__test/sel__test/prod__test/weight__test/nominal/datasets_ttbar_dl/dev1'))]"
]
},
"execution_count": 10,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"sources = [\n",
" GalleryItem(name=src[\"name\"], path=Path(src[\"path\"]))\n",
" for src in new_config.get(\"sources\", False)\n",
"]\n",
"sources"
]
},
{
"cell_type": "code",
"execution_count": 15,
"id": "a0102f9d",
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"Config(web_folder='', backup_folder='', png_dpi=400, plot_root='gallery', sources=[{'name': 'test_1_plot', 'path': 'data/cf_store/test_analysis/cf.PlotVariables1D/run2_2016_nano_v9/calib__test/sel__test/prod__test/weight__test/nominal/datasets_ttbar_dl/dev1/plot__proc_3_5606769559__cat_incl__var_jet1_pt.pdf'}, {'name': 'test_2_dir', 'path': 'data/cf_store/test_analysis/cf.PlotVariables1D/run2_2016_nano_v9/calib__test/sel__test/prod__test/weight__test/nominal/datasets_ttbar_dl/dev1/'}])"
]
},
"execution_count": 15,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"\n",
"\n",
"@dataclass\n",
"class Config:\n",
" web_folder: str = \"\"\n",
" backup_folder: str = \"\"\n",
" png_dpi: int = 400\n",
" plot_root: str = \"gallery\"\n",
" sources: list[GalleryItem] = field(default_factory=list)\n",
"\n",
" @classmethod\n",
" def from_yaml(cls, yaml_file: str, strict: bool = False) -> \"Config\":\n",
" \"\"\"\n",
" Load configuration from a YAML file.\n",
"\n",
" Args:\n",
" yaml_file (str): Path to the YAML file.\n",
" strict (bool):\n",
" If True, raises an error if a key in the YAML file does not exist in the Config class.\n",
" If False (default), adds all keys as attributes\n",
"\n",
" Returns:\n",
" Config: Instance of this class\n",
" \"\"\"\n",
"\n",
" with open(yaml_file, \"r\") as f:\n",
" new_config: dict = yaml.safe_load(f)\n",
"\n",
" new_config[\"sources\"] = [\n",
" GalleryItem(name=src[\"name\"], path=Path(src[\"path\"]))\n",
" for src in new_config.get(\"sources\", False)\n",
" ]\n",
"\n",
" instance = cls(**{\n",
" k: v\n",
" for k, v in new_config.items()\n",
" if hasattr(cls, k) or not strict\n",
" })\n",
"\n",
" for key in new_config.keys():\n",
" if strict and not hasattr(instance, key):\n",
" raise KeyError(f\"Key '{key}' not found in Config class\")\n",
"\n",
" return instance\n",
"\n",
" def to_yaml(self, yaml_file: str) -> None:\n",
" \"\"\"\n",
" Save the current configuration to a YAML file.\n",
"\n",
" Args:\n",
" yaml_file (str): Path to the YAML file.\n",
" \"\"\"\n",
" with open(yaml_file, \"w\") as f:\n",
" yaml.dump(asdict(self), f, default_flow_style=False)\n",
"\n",
"\n",
"instance = Config(**{\n",
" k: v\n",
" for k, v in new_config.items()\n",
" #if hasattr(Config, k)\n",
"})\n",
"instance"
]
},
{
"cell_type": "code",
"execution_count": 17,
"id": "0b516ae9",
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"[{'name': 'test_1_plot',\n",
" 'path': 'data/cf_store/test_analysis/cf.PlotVariables1D/run2_2016_nano_v9/calib__test/sel__test/prod__test/weight__test/nominal/datasets_ttbar_dl/dev1/plot__proc_3_5606769559__cat_incl__var_jet1_pt.pdf'},\n",
" {'name': 'test_2_dir',\n",
" 'path': 'data/cf_store/test_analysis/cf.PlotVariables1D/run2_2016_nano_v9/calib__test/sel__test/prod__test/weight__test/nominal/datasets_ttbar_dl/dev1/'}]"
]
},
"execution_count": 17,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"new_config[\"sources\"]"
]
},
{
"cell_type": "code",
"execution_count": 18,
"id": "b047f0c5",
"metadata": {},
"outputs": [
{
"data": {
"text/plain": [
"[{'name': 'test_1_plot',\n",
" 'path': 'data/cf_store/test_analysis/cf.PlotVariables1D/run2_2016_nano_v9/calib__test/sel__test/prod__test/weight__test/nominal/datasets_ttbar_dl/dev1/plot__proc_3_5606769559__cat_incl__var_jet1_pt.pdf'},\n",
" {'name': 'test_2_dir',\n",
" 'path': 'data/cf_store/test_analysis/cf.PlotVariables1D/run2_2016_nano_v9/calib__test/sel__test/prod__test/weight__test/nominal/datasets_ttbar_dl/dev1/'}]"
]
},
"execution_count": 18,
"metadata": {},
"output_type": "execute_result"
}
],
"source": [
"instance.sources"
]
}
],
"metadata": {
"kernelspec": {
"display_name": "Python 3",
"language": "python",
"name": "python3"
},
"language_info": {
"codemirror_mode": {
"name": "ipython",
"version": 3
},
"file_extension": ".py",
"mimetype": "text/x-python",
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.12.9"
}
},
"nbformat": 4,
"nbformat_minor": 5
}