Sign inSign up

cibrandocampo/synology-photos-video-enhancer

By cibrandocampo

Updated about 7 hours ago

Improves Synology Photos intermediate video quality with hardware-accelerated transcoding

Image
Content management system
Databases & storage
Monitoring & observability
0

7.6K

cibrandocampo/synology-photos-video-enhancer repository overview

Synology Photos – Video Quality Enhancer

Source on GitHub CI Docker Pulls Latest release Codecov License MIT

Python 3.14 FFmpeg (Jellyfin) amd64 · arm64 QSV · VAAPI · V4L2M2M

Synology Photos Video Enhancer logo

Fix the videos Synology Photos ruins.
Automatic re-transcoding of Synology Photos intermediate videos — H.264 High Profile or H.265/HEVC, hardware-accelerated, running on your NAS.

See the project site →
How it works, features, screenshots, codec reference and setup guide


Synology Photos, like YouTube and other streaming platforms, automatically generates lower-quality versions of uploaded videos. These intermediate videos are used for adaptive playback when the connection is not sufficient for the original file, or when the device does not support the original video's codec or resolution (for example, browsers without native HEVC support or devices such as Chromecast V1 that do not support 4K).

The problem is that Synology Photos generates these intermediate videos with very poor quality, especially when videos are uploaded via the web interface. The transcodes are created using H.264 baseline profile and a framerate of only 15 fps. The result is files that take up more space than necessary, look noticeably bad, and can even cause playback issues. Imagine trying to play your videos on a Chromecast and seeing them stutter because of the 15 fps limitation — it's simply not acceptable.

This tool solves that problem by automatically improving the quality of those intermediate videos. It retranscodes them into more efficient and modern formats (H.264 High Profile or H.265/HEVC), using hardware acceleration when available. The result is a significant improvement in visual quality while keeping file sizes efficient.

TL;DR

Synology Photos creates very low-quality intermediate videos (15 fps, H.264 baseline). This tool automatically re-transcodes them to modern formats with hardware acceleration, fixing playback issues and improving visual quality.

Features

  • Automatic transcoding: Detects and processes videos automatically
  • Hardware acceleration: Supports QSV (Intel), VAAPI (Intel/AMD), and V4L2M2M (ARM)
  • Multi-architecture: Docker images for amd64 and arm64
  • Periodic execution: Runs automatically at configurable intervals
  • Smart detection: Only transcodes videos that haven't been processed yet
  • Comprehensive logging: Detailed logging system with configurable levels
  • High test coverage: 95% code coverage ensuring reliability

Prerequisites

  • APP: Synology Photos 1.9.1 or later
  • SO: Synology DSM 7.3.2 or later
  • Docker: Version 24.0.2 or later, via Synology's "Container Manager" (recommended, as it greatly facilitates management)
  • Intel CPUs Only: SynoCli Video Drivers package 1.5.8 or later | Provides video driver support for Intel GPU acceleration, including OpenCL. Note: AMD CPUs have drivers included by default, this package is only required for Intel processors. Available from SynoCommunity.

Quick Start

  1. Create directory structure on your NAS (e.g. /volume1/docker/photo/photo-video-enhancer/)
  2. Copy docker-compose.yml and edit volume mounts to point to your photo directories
  3. Create .env from env.example and set the required dashboard credentials (WEB_PASSWORD, WEB_SECRET_KEY). Transcoding settings (codec, resolution, bitrate, etc.) are configured via the dashboard at runtime.
  4. Deploy via Synology Container Manager or docker compose up -d

For step-by-step instructions and the full environment variables reference, see the Configuration Guide.

How It Works

  1. Periodic Scanning: The application runs periodically (configurable from the dashboard)
  2. Video Detection: Recursively scans all subdirectories under /media for video files
  3. Metadata Reading: Reads original video metadata from Synology's SYNOINDEX_MEDIA_INFO files
  4. Transcoding Check: Verifies if video has already been transcoded
  5. Smart Transcoding: Only transcodes videos that haven't been processed before
  6. Output Storage: Saves transcoded videos to @eaDir/[video_name]/SYNOPHOTO_FILM_H.mp4 in the same directory as the original video
  7. Database Tracking: Maintains a SQLite database of all transcoding operations

Monitoring and Logs

After each execution, the application logs a summary:

2025-01-04T12:01:35+0000 (video-enhancer) INFO | Processing results:
2025-01-04T12:01:35+0000 (video-enhancer) INFO |   - Total processed: 514
2025-01-04T12:01:35+0000 (video-enhancer) INFO |   - Already transcoded: 239
2025-01-04T12:01:35+0000 (video-enhancer) INFO |   - Transcoded: 275
2025-01-04T12:01:35+0000 (video-enhancer) INFO |   - Errors: 0

View logs with docker logs synology-photos-video-enhancer or via Container Manager in DSM.

Dashboard

The container ships with a built-in, server-rendered dashboard that runs alongside the scheduler in the same process — no extra container, no JavaScript, no external service.

  • Access: http://<NAS-ip>:${WEB_PORT:-9200}/. Recommended setup: put it behind DSM's reverse proxy with TLS termination.
  • What it shows: total transcodings, counts per status, success rate, codec distribution, resolution distribution, the latest 5 transcodings, and the top 5 errors. HTML tables and CSS bars only.
  • About failures: a video whose dimensions cannot be determined — neither from Synology's index nor by probing the file — is recorded as failed and left untouched, rather than transcoded with guessed settings. Its path and the reason appear in the error list. Videos Synology never generated a transcoded version for are recorded as not_required, which is not a failure.

Endpoints:

MethodPathAuthPurpose
GET/requiredHTML dashboard
GET/api/statsrequiredJSON payload (same data as the HTML view)
GET/healthznone{"status":"ok"} — used by the Docker healthcheck:
GET/loginnoneLogin form
POST/loginnoneSubmit credentials
GET/logoutrequiredClear the session and redirect to /login

Authentication. Single user. Username is WEB_USER (defaults to admin); password is WEB_PASSWORD and is required — the app refuses to start if it is unset or empty. The session cookie is HMAC-signed with WEB_SECRET_KEY (also required). Generate the secret with:

python -c "import secrets; print(secrets.token_urlsafe(32))"

For the full list of dashboard env vars (port, cookie flags, etc.) see the Configuration Guide.

Upgrading

Coming from an older version? The Upgrading Guide covers what needs your attention, each entry starting from something you can observe:

  • Odd resolutions such as 44100x2 or 2x1280 in the dashboard — databases written by 4.2.2 or earlier, and how to repair them.
  • Re-encoded videos reporting a different frame rate from 4.3.0 — NTSC sources keep 29.97 instead of rounding to 30, and variable-rate sources keep their cadence.
  • More failures reported after upgrading to 4.2.3 or later — why that is intended.
  • Coming from the Grafana-based dashboard — replaced by the built-in one in 4.0.0.

Development

make dev      # Development mode (hot reload)
make debug    # Debug mode (with breakpoints)
make test     # Run all tests

For detailed development instructions, see the Development Guide.

Project Structure
src/
├── application/          # Application logic (use cases)
├── controllers/         # Controllers (entry-point orchestration)
├── domain/              # Domain models and business logic
│   ├── constants/      # Enums and constants
│   ├── models/         # Domain models
│   └── ports/          # Ports (interfaces)
└── infrastructure/      # Infrastructure adapters
    ├── config/         # Configuration management
    ├── db/             # Database adapters
    ├── filesystem/     # Filesystem operations
    ├── hardware/       # Hardware detection
    ├── transcoder/     # FFmpeg transcoding
    └── logger.py       # Logging system

For architecture details, see the Architecture Documentation. For tests, see the Testing Guide.

Documentation

DocumentDescription
Configuration GuideDirectory setup, docker-compose, environment variables
Upgrading GuideWhat needs attention when moving from an older version
Supported FormatsVideo/audio codecs, hardware acceleration, resolutions
SQLite SchemaDatabase schema documentation
Synology MetadataSYNOINDEX_MEDIA_INFO on-disk format and how it is read
Docker BuildMulti-architecture Docker build guide
ArchitectureHexagonal architecture and data flow
Development GuideLocal development, debugging, Docker dev setup
Testing GuideTest structure, fixtures, coverage

Codec Reference

Use this table to pick the right output settings in the dashboard.

Video codecs
CodecEfficiencyCPU costWebAndroidiOSTVNotes
MPEG-4×1Legacy (DivX/Xvid)
H.264 / AVC=×0.2 *Recommended — maximum compatibility
H.265 / HEVC×0.4 *Chrome/Firefox don't support it; check NAS CPU for HW encoding
AV1↑↑×22Requires NAS CPU with HW AV1 encoding support

* CPU cost with hardware acceleration (QSV/VAAPI). Without HW: H.264 ×5, H.265 ×22.

Audio codecs
CodecEfficiencyQuality †WebAndroidiOSTVNotes
AC-3 / Dolby Digital82Home theater only. Needs ≥192 kbps
MP3=75Legacy; lower quality than AAC at same bitrate
E-AC-3 / Dolby Digital Plus=91Home theater only. Possible royalty restrictions
AAC LC88Recommended — maximum compatibility
AAC HE↑↑82Ideal for low bitrates (≥48 kbps)
AAC HE v2↑↑↑70~~Stereo only; best at ≤48 kbps

† MUSHRA perceptual quality score at 128 kbps (0–100). ~ = partial support depending on device.

Software Architecture

Uses Hexagonal Architecture (Ports and Adapters) pattern to ensure:

  • Clear separation between domain logic and infrastructure
  • Easy testing with mocked dependencies
  • Flexibility to swap implementations (e.g., different filesystems, databases)

References

Acknowledgments

This project would not be possible without the following open-source projects:

  • FFmpeg: The powerful multimedia framework that enables video transcoding with hardware acceleration. Thank you to the FFmpeg team for their incredible work.
  • Jellyfin: Special thanks to the Jellyfin project for providing pre-built FFmpeg binaries with hardware acceleration drivers included. This significantly simplifies Docker image management and ensures reliable hardware acceleration support. Specifically, we use the jellyfin-ffmpeg project.
  • Python: The programming language that powers this application.

Support

License

Licensed under the MIT License. See LICENSE for details.

Note on Dependencies:

  • This project uses Jellyfin FFmpeg binaries, which are licensed under LGPL-3.0/GPL-2.0/GPL-3.0 (see jellyfin-ffmpeg license). The FFmpeg binaries are used as external tools and are not modified or statically linked, which is compatible with the MIT license of this project.

Tag summary

Content type

Image

Digest

sha256:7960416ff

Size

178.2 MB

Last updated

about 2 months ago

docker pull cibrandocampo/synology-photos-video-enhancer